My app (C++, Windows) is communicating with an external device. If the device doesn’t answer after certain period of time, I want to reset a status variable.
My initial approach would be
auto timer = boost::asio::deadline_timer(io_svc);
timer.expires_from_now(boost::posix_time::seconds(10));
timer.async_wait(boost::bind(&Class::CurrRequestTimeout, this, boost::asio::placeholders::error));
io_svc.poll();
and the timeout function
void Class::CurrRequestTimeout(const boost::system::error_code & ec)
{
if (ec)
{
// this timeout was canceled
return;
}
ResetStatusVariable();
}
This should be non-blocking, that’s why I selected poll() instead of run() (seen here). However, with poll() the timeout method is never called. With run() it works just fine, but this blocks the execution.
The
pollfunction only runs handlers that are ready to run at that instant. Since the timer hasn’t timed out yet, it can’t run that handler now. And you asked it not to block. So what would you expect it to do?If your code is thread safe, create another thread that can block in
run. If not, then this thread has to come back and callpolllater to give handlers a chance to run.One caveat: If you do create one or more
runthreads, you need to make sure there’s always at least one event to wait for, or the thread will be unable to wait for a handler.boost::asio::io_service::workis there for just this purpose. See this question.