[#associators] == Associators `cobalt` uses the `associator` concept of asio, but simplifies it. That is, it has three associators that are member functions of an awaiting promise. - `const executor_type & get_executor()` (always `executor`, must return by const ref) - `allocator_type get_allocator()` (always `pmr::polymorphic_allocator`) - `cancellation_slot_type get_cancellation_slot()` (must have the same IF as `asio::cancellation_slot`) `cobalt` uses concepts to check if those are present in its `await_suspend` functions. That way custom coroutines can support cancellation, executors and allocators. In a custom awaitable you can obtain them like this: [source,cpp] ---- struct my_awaitable { bool await_ready(); template void await_suspend(std::corutine_handle

h) { if constexpr (requires (Promise p) {p.get_executor();}) handle_executor(h.promise().get_executor(); if constexpr (requires (Promise p) {p.get_cancellation_slot();}) if ((cl = h.promise().get_cancellation_slot()).is_connected()) cl.emplace(); } void await_resume(); }; ---- Cancellation gets connected in a `co_await` expression (if supported by the coroutine & awaitable), including synchronization mechanism like <>.