c++multithreadingboostfibers

boost fibers work_stealing barrier causes segfault


This is a completed version of an example I found somewhere in the boost docs on how to spawn worker threads to use with fibers work_stealing algo.

#include <iostream>
#include <chrono>
#include <boost/fiber/all.hpp>

int main() {
    size_t count = std::thread::hardware_concurrency();
    boost::fibers::barrier b{count};
    for(int i=0;i<count;i++) {
        new std::thread([&b, &count] {
            boost::fibers::use_scheduling_algorithm<boost::fibers::algo::work_stealing>(count);
            b.wait();
        });
    }
    std::this_thread::sleep_for(std::chrono::seconds(5));
    return 0;
}

This causes a segfault most of the time and I don't understand why.

Here the cmake file:

cmake_minimum_required(VERSION 3.12)
set(CMAKE_CXX_STANDARD 17)

set(VERSION 1_68_0)
set(BOOST_ROOT /home/User/boost_${VERSION})

find_package(Boost REQUIRED COMPONENTS fiber)
find_package(Threads)

include_directories(${Boost_INCLUDE_DIRS})
add_executable(test test.cpp)
target_link_libraries(test ${Boost_LIBRARIES} ${CMAKE_THREAD_LIBS_INIT})

I am running Fedora 28 and built Boost from source with gcc 8.1.1 and didn't install it. The project is built with the same compiler. (libc++ isn't installed anywhere.) I get the same behaviour with git branches master and develop as well as 1_67_0. I feel like I'm missing something obvious here.


Solution

  • It's a bug that will be fixed in branch develop. The problem is that the registration of the work-stealing algos at the internal container is not properly synchronized. Your example would look like:

    size_t count = std::thread::hardware_concurrency();
    for(size_t i=1;i<count;i++) {
        new std::thread([&count] {
            boost::fibers::use_scheduling_algorithm<boost::fibers::algo::work_stealing>(count);
        });
    }
    boost::fibers::use_scheduling_algorithm<boost::fibers::algo::work_stealing>(count);