Skip to content
Open
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
22 changes: 19 additions & 3 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -151,8 +151,11 @@ jobs:
if: env.B2_USE_CCACHE
with:
path: ~/.ccache
key: ${{matrix.os}}-${{matrix.container}}-${{matrix.compiler}}-${{github.sha}}
restore-keys: ${{matrix.os}}-${{matrix.container}}-${{matrix.compiler}}-
key: ccache-${{matrix.os}}-${{matrix.compiler}}-${{ hashFiles('**/*.cpp', '**/*.hpp', '**/*.c', '**/*.h') }}
restore-keys: |
ccache-${{matrix.os}}-${{matrix.compiler}}-
ccache-${{matrix.os}}-
ccache-

- name: Install packages
if: matrix.install
Expand Down Expand Up @@ -239,7 +242,7 @@ jobs:
os: windows-2022
supported: true
- toolset: clang-win
cxxstd: "14,17,20,latest"
cxxstd: "latest,20,17,14"
addrmd: 32,64
os: windows-2022
supported: true
Expand Down Expand Up @@ -353,6 +356,9 @@ jobs:
git submodule update --init tools/boostdep
python tools/boostdep/depinst/depinst.py --git_args "--jobs 3" $LIBRARY

# HACK: boost.functional seems to be missing?
git submodule update --init libs/functional

- name: Use library with add_subdirectory
run: |
cd ../boost-root/libs/$LIBRARY/test/cmake_subdir_test
Expand Down Expand Up @@ -409,6 +415,8 @@ jobs:
git submodule update --init tools/boostdep
python tools/boostdep/depinst/depinst.py --git_args "--jobs 3" $LIBRARY

git submodule update --init libs/functional

- name: Configure
run: |
cd ../boost-root
Expand Down Expand Up @@ -475,6 +483,8 @@ jobs:
git submodule update --init tools/boostdep
python tools/boostdep/depinst/depinst.py --git_args "--jobs 3" $LIBRARY

git submodule update --init libs/functional

- name: Configure
run: |
cd ../boost-root
Expand Down Expand Up @@ -527,6 +537,8 @@ jobs:
git submodule update --init tools/boostdep
python tools/boostdep/depinst/depinst.py --git_args "--jobs 3" %LIBRARY%

git submodule update --init libs/functional

- name: Use library with add_subdirectory (Debug)
shell: cmd
run: |
Expand Down Expand Up @@ -580,6 +592,8 @@ jobs:
git submodule update --init tools/boostdep
python tools/boostdep/depinst/depinst.py --git_args "--jobs 3" %LIBRARY%

git submodule update --init libs/functional

- name: Configure
shell: cmd
run: |
Expand Down Expand Up @@ -651,6 +665,8 @@ jobs:
git submodule update --init tools/boostdep
python tools/boostdep/depinst/depinst.py --git_args "--jobs 3" %LIBRARY%

git submodule update --init libs/functional

- name: Configure
shell: cmd
run: |
Expand Down
4 changes: 2 additions & 2 deletions include/boost/lockfree/detail/freelist.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ namespace boost { namespace lockfree { namespace detail {
template < typename T, typename Alloc = std::allocator< T > >
class alignas( cacheline_bytes ) freelist_stack : Alloc
{
struct freelist_node
struct BOOST_MAY_ALIAS freelist_node
{
tagged_ptr< freelist_node > next;
};
Expand Down Expand Up @@ -395,7 +395,7 @@ struct runtime_sized_freelist_storage : boost::alignment::aligned_allocator_adap
template < typename T, typename NodeStorage = runtime_sized_freelist_storage< T > >
class fixed_size_freelist : NodeStorage
{
struct freelist_node
struct BOOST_MAY_ALIAS freelist_node
{
tagged_index next;
};
Expand Down
54 changes: 37 additions & 17 deletions include/boost/lockfree/queue.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,7 @@ class queue
static constexpr bool node_based = !( has_capacity || fixed_sized );
static constexpr bool compile_time_sized = has_capacity;

struct alignas( detail::cacheline_bytes ) node
struct BOOST_MAY_ALIAS node
{
typedef typename detail::select_tagged_handle< node, node_based >::tagged_handle_type tagged_node_handle;
typedef typename detail::select_tagged_handle< node, node_based >::handle_type handle_type;
Expand All @@ -125,8 +125,8 @@ class queue
node( void )
{}

atomic< tagged_node_handle > next;
T data;
alignas( detail::cacheline_bytes ) atomic< tagged_node_handle > next;
T data;
};

typedef detail::extract_allocator_t< bound_args, node > node_allocator;
Expand Down Expand Up @@ -177,8 +177,6 @@ class queue
requires( has_capacity )
#endif
:
head_( tagged_node_handle( 0, 0 ) ),
tail_( tagged_node_handle( 0, 0 ) ),
pool( node_allocator(), capacity )
{
// Don't use BOOST_STATIC_ASSERT() here since it will be evaluated when compiling
Expand All @@ -191,10 +189,13 @@ class queue
*
* \pre Must specify a capacity<> argument
* */
#if !defined( BOOST_NO_CXX20_HDR_CONCEPTS )
template < typename U >
requires( has_capacity )
#else
template < typename U, typename Enabler = std::enable_if< has_capacity > >
#endif
explicit queue( typename boost::allocator_rebind< node_allocator, U >::type const& alloc ) :
head_( tagged_node_handle( 0, 0 ) ),
tail_( tagged_node_handle( 0, 0 ) ),
pool( alloc, capacity )
{
initialize();
Expand All @@ -204,10 +205,14 @@ class queue
*
* \pre Must specify a capacity<> argument
* */
#if !defined( BOOST_NO_CXX20_HDR_CONCEPTS )
explicit queue( allocator const& alloc )
requires( has_capacity )
:
#else
template < typename Enabler = std::enable_if< has_capacity > >
explicit queue( allocator const& alloc ) :
head_( tagged_node_handle( 0, 0 ) ),
tail_( tagged_node_handle( 0, 0 ) ),
#endif
pool( alloc, capacity )
{
initialize();
Expand All @@ -219,10 +224,14 @@ class queue
*
* \pre Must \b not specify a capacity<> argument
* */
#if !defined( BOOST_NO_CXX20_HDR_CONCEPTS )
explicit queue( size_type n )
requires( !has_capacity )
:
#else
template < typename Enabler = std::enable_if< !has_capacity > >
explicit queue( size_type n ) :
head_( tagged_node_handle( 0, 0 ) ),
tail_( tagged_node_handle( 0, 0 ) ),
#endif
pool( node_allocator(), n + 1 )
{
initialize();
Expand All @@ -234,10 +243,13 @@ class queue
*
* \pre Must \b not specify a capacity<> argument
* */
#if !defined( BOOST_NO_CXX20_HDR_CONCEPTS )
template < typename U >
requires( !has_capacity )
#else
template < typename U, typename Enabler = std::enable_if< !has_capacity > >
#endif
queue( size_type n, typename boost::allocator_rebind< node_allocator, U >::type const& alloc ) :
head_( tagged_node_handle( 0, 0 ) ),
tail_( tagged_node_handle( 0, 0 ) ),
pool( alloc, n + 1 )
{
initialize();
Expand All @@ -249,10 +261,14 @@ class queue
*
* \pre Must \b not specify a capacity<> argument
* */
#if !defined( BOOST_NO_CXX20_HDR_CONCEPTS )
queue( size_type n, allocator const& alloc )
requires( !has_capacity )
:
#else
template < typename Enabler = std::enable_if< !has_capacity > >
queue( size_type n, allocator const& alloc ) :
head_( tagged_node_handle( 0, 0 ) ),
tail_( tagged_node_handle( 0, 0 ) ),
#endif
pool( alloc, n + 1 )
{
initialize();
Expand Down Expand Up @@ -625,8 +641,12 @@ class queue

private:
#ifndef BOOST_DOXYGEN_INVOKED
atomic< tagged_node_handle > head_;
alignas( detail::cacheline_bytes ) atomic< tagged_node_handle > tail_;
atomic< tagged_node_handle > head_ {
tagged_node_handle( 0, 0 ),
};
alignas( detail::cacheline_bytes ) atomic< tagged_node_handle > tail_ {
tagged_node_handle( 0, 0 ),
};

pool_t pool;
#endif
Expand Down
54 changes: 46 additions & 8 deletions include/boost/lockfree/spsc_queue.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -43,13 +43,11 @@ class ringbuffer_base
#ifndef BOOST_DOXYGEN_INVOKED
protected:
typedef std::size_t size_t;
alignas( cacheline_bytes ) atomic< size_t > write_index_;
alignas( cacheline_bytes ) atomic< size_t > read_index_;
alignas( cacheline_bytes ) atomic< size_t > write_index_ {};
alignas( cacheline_bytes ) atomic< size_t > read_index_ {};

protected:
ringbuffer_base( void ) :
write_index_( 0 ),
read_index_( 0 )
ringbuffer_base( void )
{}

static size_t next_index( size_t arg, size_t max_size )
Expand Down Expand Up @@ -653,7 +651,12 @@ class spsc_queue : public detail::make_ringbuffer< T, Options... >::ringbuffer_t
*
* \note This is just for API compatibility: an allocator isn't actually needed
*/
#if !defined( BOOST_NO_CXX20_HDR_CONCEPTS )
template < typename U >
requires( !runtime_sized )
#else
template < typename U, typename Enabler = std::enable_if< !runtime_sized > >
#endif
explicit spsc_queue( typename boost::allocator_rebind< allocator, U >::type const& )
{}

Expand All @@ -663,24 +666,40 @@ class spsc_queue : public detail::make_ringbuffer< T, Options... >::ringbuffer_t
*
* \note This is just for API compatibility: an allocator isn't actually needed
*/
#if !defined( BOOST_NO_CXX20_HDR_CONCEPTS )
explicit spsc_queue( allocator const& )
requires( !runtime_sized )
#else
template < typename Enabler = std::enable_if< !runtime_sized > >
explicit spsc_queue( allocator const& )
#endif
{}

/** Constructs a spsc_queue for element_count elements
*
* \pre spsc_queue must be configured to be sized at run-time
*/
#if !defined( BOOST_NO_CXX20_HDR_CONCEPTS )
explicit spsc_queue( size_type element_count )
requires( runtime_sized )
#else
template < typename Enabler = std::enable_if< runtime_sized > >
explicit spsc_queue( size_type element_count ) :
explicit spsc_queue( size_type element_count )
#endif
:
base_type( element_count )
{}

/** Constructs a spsc_queue for element_count elements with a custom allocator
*
* \pre spsc_queue must be configured to be sized at run-time
*/
#if !defined( BOOST_NO_CXX20_HDR_CONCEPTS )
template < typename U >
requires( runtime_sized )
#else
template < typename U, typename Enabler = std::enable_if< runtime_sized > >
#endif
spsc_queue( size_type element_count, typename boost::allocator_rebind< allocator, U >::type const& alloc ) :
base_type( alloc, element_count )
{}
Expand All @@ -689,8 +708,14 @@ class spsc_queue : public detail::make_ringbuffer< T, Options... >::ringbuffer_t
*
* \pre spsc_queue must be configured to be sized at run-time
*/
#if !defined( BOOST_NO_CXX20_HDR_CONCEPTS )
spsc_queue( size_type element_count, allocator_arg const& alloc )
requires( runtime_sized )
#else
template < typename Enabler = std::enable_if< runtime_sized > >
spsc_queue( size_type element_count, allocator_arg const& alloc ) :
spsc_queue( size_type element_count, allocator_arg const& alloc )
#endif
:
base_type( alloc, element_count )
{}

Expand Down Expand Up @@ -739,7 +764,12 @@ class spsc_queue : public detail::make_ringbuffer< T, Options... >::ringbuffer_t
*
* \note Thread-safe and wait-free
*/
#if !defined( BOOST_NO_CXX20_HDR_CONCEPTS )
template < typename U >
requires( std::is_convertible_v< T, U > )
#else
template < typename U, typename Enabler = std::enable_if< std::is_convertible< T, U >::value > >
#endif
bool pop( U& ret )
{
return consume_one( [ & ]( T&& t ) {
Expand Down Expand Up @@ -866,8 +896,16 @@ class spsc_queue : public detail::make_ringbuffer< T, Options... >::ringbuffer_t
*
* \note Thread-safe and wait-free
* */
#if !defined( BOOST_NO_CXX20_HDR_CONCEPTS )
template < typename OutputIterator >
typename std::enable_if< !std::is_convertible< T, OutputIterator >::value, size_type >::type pop( OutputIterator it )
requires( !std::is_convertible_v< T, OutputIterator > )
size_type
#else
template < typename OutputIterator,
typename Enabler = std::enable_if< !std::is_convertible< T, OutputIterator >::value > >
typename std::enable_if< !std::is_convertible< T, OutputIterator >::value, size_type >::type
#endif
pop( OutputIterator it )
{
return base_type::pop_to_output_iterator( it );
}
Expand Down
Loading