[Boost-bugs] [Boost C++ Libraries] #13570: asio_handler_invoke resume wrong thread in coroutine

Subject: [Boost-bugs] [Boost C++ Libraries] #13570: asio_handler_invoke resume wrong thread in coroutine
From: Boost C++ Libraries (noreply_at_[hidden])
Date: 2018-05-21 09:58:20


#13570: asio_handler_invoke resume wrong thread in coroutine
-------------------------------------------------+-------------------------
 Reporter: pengying.wu@… | Owner:
                                                 | chris_kohlhoff
     Type: Bugs | Status: new
Milestone: To Be Determined | Component: asio
  Version: Boost 1.67.0 | Severity: Problem
 Keywords: asio, coroutine, |
  asio_handler_invoke |
-------------------------------------------------+-------------------------
 Environment:\\
 Windows 10, VS2015 Update3, Boost 1.65.1, Boost 1.67.0, x86/x64\\

 Coroutine should be suspended and resumed by the same thread, but in boost
 1.67.0 it doesn't. I guess it's a bug introduced since boost 1.66.

 In Boost 1.65.0, correct behavior, output:\\
 thread : 37c0\\
 thread : 37c0\\
 hello\\

 In Boost 1.67.0, wrong behavior, output:\\
 thread : df4\\
 thread : 1844\\
 hello\\

 {{{
 #include <iostream>
 #include <boost/asio.hpp>
 #include <boost/asio/spawn.hpp>
 #include <boost/bind.hpp>
 #include <boost/thread.hpp>

 std::string Test(boost::asio::io_service& ios,
     boost::asio::yield_context yield)
 {
     boost::asio::io_service::work work(ios);

 #if BOOST_VERSION >= 106600
     boost::asio::async_completion<
         boost::asio::yield_context,
         void(boost::system::error_code, std::string)>
         init(BOOST_ASIO_MOVE_CAST(boost::asio::yield_context)(yield));
     auto handler = init.completion_handler;

 #else
     boost::asio::detail::async_result_init<
         boost::asio::yield_context,
         void(boost::system::error_code, std::string)>
         init(BOOST_ASIO_MOVE_CAST(boost::asio::yield_context)(yield));
     auto handler = init.handler;
 #endif

     boost::thread t([&handler]() {

         boost::this_thread::sleep_for(boost::chrono::seconds(2));
         boost::asio::detail::asio_handler_invoke(
             boost::bind<void>(
                 handler, boost::system::error_code(), "hello"), &handler);

     });
     t.detach();

     return init.result.get();

 }

 int main(int argc, char* argv[])
 {
     boost::asio::io_service ios;

     boost::asio::spawn(ios, [&ios](boost::asio::yield_context yield) {

         boost::system::error_code ec;
         std::cout << "thread : " << boost::this_thread::get_id() <<
 std::endl;
         std::string msg = Test(ios, yield[ec]);
         std::cout << "thread : " << boost::this_thread::get_id() <<
 std::endl;
         std::cout << msg << std::endl;

     });

     ios.run();

     std::string tmp;
     std::cin >> tmp;

     return 0;

 }
 }}}

-- 
Ticket URL: <https://svn.boost.org/trac10/ticket/13570>
Boost C++ Libraries <http://www.boost.org/>
Boost provides free peer-reviewed portable C++ source libraries.

This archive was generated by hypermail 2.1.7 : 2018-05-21 10:02:56 UTC