Spawn a new coroutined-based thread of execution.
template< typename Executor, typename F, typename CompletionToken = DEFAULT> DEDUCED co_spawn( const Executor & ex, F && f, CompletionToken && token = DEFAULT, typename constraint< is_executor< Executor >::value||execution::is_executor< Executor >::value >::type = 0);
The executor that will be used to schedule the new thread of execution.
A nullary function object with a return type of the form asio::awaitable<R,E>
that will be used as the coroutine's entry point.
The completion
token that will handle the notification that the thread of
execution has completed. If R
is void
, the function
signature of the completion handler must be:
void handler(std::exception_ptr);
Otherwise, the function signature of the completion handler must be:
void handler(std::exception_ptr, R);
void(std::exception_ptr, R)
where R
is the first template
argument to the awaitable
returned by the supplied function object F:
asio::awaitable<R, AwaitableExecutor> F()
asio::awaitable<std::size_t> echo(tcp::socket socket) { std::size_t bytes_transferred = 0; try { char data[1024]; for (;;) { std::size_t n = co_await socket.async_read_some( asio::buffer(data), asio::use_awaitable); co_await asio::async_write(socket, asio::buffer(data, n), asio::use_awaitable); bytes_transferred += n; } } catch (const std::exception&) { } co_return bytes_transferred; } // ... asio::co_spawn(my_executor, [socket = std::move(my_tcp_socket)]() mutable -> asio::awaitable<void> { try { char data[1024]; for (;;) { std::size_t n = co_await socket.async_read_some( asio::buffer(data), asio::use_awaitable); co_await asio::async_write(socket, asio::buffer(data, n), asio::use_awaitable); } } catch (const std::exception& e) { std::cerr << "Exception: " << e.what() << "\n"; } }, asio::detached);
The new thread of execution is created with a cancellation state that supports
cancellation_type::terminal
values only. To change the cancellation
state, call this_coro::reset_cancellation_state
.