ASIO: acceptor::async_accept throws "Operation cancelled" after restart io_service
Hi, In short my program: - creates an io_service - calls acceptor::async_accept - calls io_service.run - handle several connections OK - calls io_service.stop - the acceptor goes out of scope (i.e. the destructor of the owning object is ran) - calls io_service.restart - calls acceptor::async_accept which then throws "Operation cancelled" Should it be possible to do this? When/under what circumstances does async_accept throw this exception? Could it be connected with the fact that the acceptor's destructors documents that is does some cleanup but actually does nothing, from the source: /// Destroys the acceptor. /** * This function destroys the acceptor, cancelling any outstanding * asynchronous operations associated with the acceptor as if by calling * @c cancel. */ ~basic_socket_acceptor() { } OS: Linux Debian Bullseye, Boost 1.74, gcc 10 TIA Joost
On Mon, 19 Apr 2021 at 20:39, Joost Kraaijeveld via Boost-users < boost-users@lists.boost.org> wrote:
Hi,
In short my program: - creates an io_service - calls acceptor::async_accept - calls io_service.run - handle several connections OK - calls io_service.stop - the acceptor goes out of scope (i.e. the destructor of the owning object is ran) - calls io_service.restart - calls acceptor::async_accept which then throws "Operation cancelled"
Should it be possible to do this? When/under what circumstances does async_accept throw this exception?
Difficult to comment without compiling up the code and trying it locally. Are you able to share a git repo that I can build? (cmake if possible) Thanks.
Could it be connected with the fact that the acceptor's destructors documents that is does some cleanup but actually does nothing, from the source:
/// Destroys the acceptor. /** * This function destroys the acceptor, cancelling any outstanding * asynchronous operations associated with the acceptor as if by calling * @c cancel. */ ~basic_socket_acceptor() { }
OS: Linux Debian Bullseye, Boost 1.74, gcc 10
TIA
Joost
_______________________________________________ Boost-users mailing list Boost-users@lists.boost.org https://lists.boost.org/mailman/listinfo.cgi/boost-users
On 20/04/2021 5:27 am, Joost Kraaijeveld wrote:
In short my program: - creates an io_service - calls acceptor::async_accept - calls io_service.run - handle several connections OK - calls io_service.stop - the acceptor goes out of scope (i.e. the destructor of the owning object is ran) - calls io_service.restart - calls acceptor::async_accept which then throws "Operation cancelled"
Should it be possible to do this? When/under what circumstances does async_accept throw this exception?
Yes, that's normal. Async operations are typically automatically cancelled when the related I/O object is destroyed, but the callback is still queued. But it can't actually run until you have a thread running the I/O service. This is part of why it's usually recommended to pass a shared_ptr to your owning object into callbacks, to keep them alive longer than the I/O object itself. (There is *always* a callback at the end of every async operation. Even if just to say that it was cancelled.) io_service.stop() simply stops the thread pool, it doesn't do anything else. When you start it again then any previously queued callbacks will be able to execute.
participants (3)
-
Gavin Lambert
-
Joost Kraaijeveld
-
Richard Hodges