I'm using the latest ASIO version(as of this time 1.18.0). Currently designing a multithreaded asynchronous TCP server with timers(for timeouts). I have a single io_context
with multiple threads calling its run()
function. I accept new connections like this:
void Server::AcceptConnection()
{
acceptor_.async_accept(asio::make_strand(io_context_),
[this](const asio::error_code& error, asio::ip::tcp::socket peer) {
if (!error) {
std::make_shared<Session>(std::move(peer))->run();
}
AcceptConnection();
});
}
And here a stripped down version of the Session
class:
class Session : public std::enable_shared_from_this<Session>
{
public:
Session(asio::ip::tcp::socket&& peer) : peer_(std::move(peer)) {}
void run()
{
/*
asio::async_read(peer_, some_buffers_, some_callback_);
timeout_timer_.expires_after();
timeout_timer_.async_wait();
// etc
*/
}
private:
asio::ip::tcp::socket peer_;
asio::steady_timer timeout_timer_{peer_.get_executor()};
}
Please note the initialization of the timer.
Also, beware that I'm not using any kind of strand::wrap()
or asio::bind_executor()
wrappers for the async handlers of the socket and the timer, because of what I understood, they are no longer required if I initialize my objects with the proper executors.
The question here is: Is that a correct way of handling TCP connection inside a strand with a timer inside the same strand that the TCP connection is using?
Note: The timer is used to abort the TCP connection if the timeout passes.