Skip to content

[libc++] Extract a clean base support API for std::atomic #118129

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 4 commits into from
Dec 9, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion libcxx/include/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -212,11 +212,13 @@ set(files
__atomic/atomic_sync.h
__atomic/check_memory_order.h
__atomic/contention_t.h
__atomic/cxx_atomic_impl.h
__atomic/fence.h
__atomic/is_always_lock_free.h
__atomic/kill_dependency.h
__atomic/memory_order.h
__atomic/support.h
__atomic/support/c11.h
__atomic/support/gcc.h
__atomic/to_gcc_order.h
__bit/bit_cast.h
__bit/bit_ceil.h
Expand Down
2 changes: 1 addition & 1 deletion libcxx/include/__atomic/atomic.h
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,9 @@

#include <__atomic/atomic_sync.h>
#include <__atomic/check_memory_order.h>
#include <__atomic/cxx_atomic_impl.h>
#include <__atomic/is_always_lock_free.h>
#include <__atomic/memory_order.h>
#include <__atomic/support.h>
#include <__config>
#include <__cstddef/ptrdiff_t.h>
#include <__functional/operations.h>
Expand Down
2 changes: 1 addition & 1 deletion libcxx/include/__atomic/atomic_flag.h
Original file line number Diff line number Diff line change
Expand Up @@ -11,8 +11,8 @@

#include <__atomic/atomic_sync.h>
#include <__atomic/contention_t.h>
#include <__atomic/cxx_atomic_impl.h>
#include <__atomic/memory_order.h>
#include <__atomic/support.h>
#include <__chrono/duration.h>
#include <__config>
#include <__memory/addressof.h>
Expand Down
1 change: 0 additions & 1 deletion libcxx/include/__atomic/atomic_sync.h
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@
#define _LIBCPP___ATOMIC_ATOMIC_SYNC_H

#include <__atomic/contention_t.h>
#include <__atomic/cxx_atomic_impl.h>
#include <__atomic/memory_order.h>
#include <__atomic/to_gcc_order.h>
#include <__chrono/duration.h>
Expand Down
2 changes: 1 addition & 1 deletion libcxx/include/__atomic/contention_t.h
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
#ifndef _LIBCPP___ATOMIC_CONTENTION_T_H
#define _LIBCPP___ATOMIC_CONTENTION_T_H

#include <__atomic/cxx_atomic_impl.h>
#include <__atomic/support.h>
#include <__config>
#include <cstdint>

Expand Down
2 changes: 1 addition & 1 deletion libcxx/include/__atomic/fence.h
Original file line number Diff line number Diff line change
Expand Up @@ -9,8 +9,8 @@
#ifndef _LIBCPP___ATOMIC_FENCE_H
#define _LIBCPP___ATOMIC_FENCE_H

#include <__atomic/cxx_atomic_impl.h>
#include <__atomic/memory_order.h>
#include <__atomic/support.h>
#include <__config>

#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
Expand Down
124 changes: 124 additions & 0 deletions libcxx/include/__atomic/support.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,124 @@
//===----------------------------------------------------------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#ifndef _LIBCPP___ATOMIC_SUPPORT_H
#define _LIBCPP___ATOMIC_SUPPORT_H

#include <__config>
#include <__type_traits/is_trivially_copyable.h>

#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
# pragma GCC system_header
#endif

//
// This file implements base support for atomics on the platform.
//
// The following operations and types must be implemented (where _Atmc
// is __cxx_atomic_base_impl for readability):
//
// clang-format off
//
// template <class _Tp>
// struct __cxx_atomic_base_impl;
//
// #define __cxx_atomic_is_lock_free(__size)
//
// void __cxx_atomic_thread_fence(memory_order __order) noexcept;
// void __cxx_atomic_signal_fence(memory_order __order) noexcept;
//
// template <class _Tp>
// void __cxx_atomic_init(_Atmc<_Tp> volatile* __a, _Tp __val) noexcept;
// template <class _Tp>
// void __cxx_atomic_init(_Atmc<_Tp>* __a, _Tp __val) noexcept;
//
// template <class _Tp>
// void __cxx_atomic_store(_Atmc<_Tp> volatile* __a, _Tp __val, memory_order __order) noexcept;
// template <class _Tp>
// void __cxx_atomic_store(_Atmc<_Tp>* __a, _Tp __val, memory_order __order) noexcept;
//
// template <class _Tp>
// _Tp __cxx_atomic_load(_Atmc<_Tp> const volatile* __a, memory_order __order) noexcept;
// template <class _Tp>
// _Tp __cxx_atomic_load(_Atmc<_Tp> const* __a, memory_order __order) noexcept;
//
// template <class _Tp>
// void __cxx_atomic_load_inplace(_Atmc<_Tp> const volatile* __a, _Tp* __dst, memory_order __order) noexcept;
// template <class _Tp>
// void __cxx_atomic_load_inplace(_Atmc<_Tp> const* __a, _Tp* __dst, memory_order __order) noexcept;
//
// template <class _Tp>
// _Tp __cxx_atomic_exchange(_Atmc<_Tp> volatile* __a, _Tp __value, memory_order __order) noexcept;
// template <class _Tp>
// _Tp __cxx_atomic_exchange(_Atmc<_Tp>* __a, _Tp __value, memory_order __order) noexcept;
//
// template <class _Tp>
// bool __cxx_atomic_compare_exchange_strong(_Atmc<_Tp> volatile* __a, _Tp* __expected, _Tp __value, memory_order __success, memory_order __failure) noexcept;
// template <class _Tp>
// bool __cxx_atomic_compare_exchange_strong(_Atmc<_Tp>* __a, _Tp* __expected, _Tp __value, memory_order __success, memory_order __failure) noexcept;
//
// template <class _Tp>
// bool __cxx_atomic_compare_exchange_weak(_Atmc<_Tp> volatile* __a, _Tp* __expected, _Tp __value, memory_order __success, memory_order __failure) noexcept;
// template <class _Tp>
// bool __cxx_atomic_compare_exchange_weak(_Atmc<_Tp>* __a, _Tp* __expected, _Tp __value, memory_order __success, memory_order __failure) noexcept;
//
// template <class _Tp>
// _Tp __cxx_atomic_fetch_add(_Atmc<_Tp> volatile* __a, _Tp __delta, memory_order __order) noexcept;
// template <class _Tp>
// _Tp __cxx_atomic_fetch_add(_Atmc<_Tp>* __a, _Tp __delta, memory_order __order) noexcept;
//
// template <class _Tp>
// _Tp* __cxx_atomic_fetch_add(_Atmc<_Tp*> volatile* __a, ptrdiff_t __delta, memory_order __order) noexcept;
// template <class _Tp>
// _Tp* __cxx_atomic_fetch_add(_Atmc<_Tp*>* __a, ptrdiff_t __delta, memory_order __order) noexcept;
//
// template <class _Tp>
// _Tp __cxx_atomic_fetch_sub(_Atmc<_Tp> volatile* __a, _Tp __delta, memory_order __order) noexcept;
// template <class _Tp>
// _Tp __cxx_atomic_fetch_sub(_Atmc<_Tp>* __a, _Tp __delta, memory_order __order) noexcept;
// template <class _Tp>
// _Tp* __cxx_atomic_fetch_sub(_Atmc<_Tp*> volatile* __a, ptrdiff_t __delta, memory_order __order) noexcept;
// template <class _Tp>
// _Tp* __cxx_atomic_fetch_sub(_Atmc<_Tp*>* __a, ptrdiff_t __delta, memory_order __order) noexcept;
//
// template <class _Tp>
// _Tp __cxx_atomic_fetch_and(_Atmc<_Tp> volatile* __a, _Tp __pattern, memory_order __order) noexcept;
// template <class _Tp>
// _Tp __cxx_atomic_fetch_and(_Atmc<_Tp>* __a, _Tp __pattern, memory_order __order) noexcept;
//
// template <class _Tp>
// _Tp __cxx_atomic_fetch_or(_Atmc<_Tp> volatile* __a, _Tp __pattern, memory_order __order) noexcept;
// template <class _Tp>
// _Tp __cxx_atomic_fetch_or(_Atmc<_Tp>* __a, _Tp __pattern, memory_order __order) noexcept;
// template <class _Tp>
// _Tp __cxx_atomic_fetch_xor(_Atmc<_Tp> volatile* __a, _Tp __pattern, memory_order __order) noexcept;
// template <class _Tp>
// _Tp __cxx_atomic_fetch_xor(_Atmc<_Tp>* __a, _Tp __pattern, memory_order __order) noexcept;
//
// clang-format on
//

#if _LIBCPP_HAS_GCC_ATOMIC_IMP
# include <__atomic/support/gcc.h>
#elif _LIBCPP_HAS_C_ATOMIC_IMP
# include <__atomic/support/c11.h>
#endif

_LIBCPP_BEGIN_NAMESPACE_STD

template <typename _Tp, typename _Base = __cxx_atomic_base_impl<_Tp> >
struct __cxx_atomic_impl : public _Base {
static_assert(is_trivially_copyable<_Tp>::value, "std::atomic<T> requires that 'T' be a trivially copyable type");

_LIBCPP_HIDE_FROM_ABI __cxx_atomic_impl() _NOEXCEPT = default;
_LIBCPP_HIDE_FROM_ABI _LIBCPP_CONSTEXPR explicit __cxx_atomic_impl(_Tp __value) _NOEXCEPT : _Base(__value) {}
};

_LIBCPP_END_NAMESPACE_STD

#endif // _LIBCPP___ATOMIC_SUPPORT_H
Loading
Loading