[Boost][asio]How add a timeout to asio connection?
Hi All, I have one problem, I have this class to connect to my server app: class session { public: static void init( const std::string& host, const std::string& port, hades::archive::archive& iarch, hades::archive::archive& oarch) { boost::asio::io_service io_service; client client(io_service, host, port, iarch, oarch); io_service.run(); } }; The problem is : if my server is down, my client (session) will block on io_service.run(); the client nerves end. Then I try to add a time out: class client { public: /// Constructor starts the asynchronous connect operation. client(boost::asio::io_service& io_service, const std::string& host, const std::string& port, // service hades::archive::archive& iarch, hades::archive::archive& oarch) : connection_(io_service) , deadline_(io_service) , iarch_(&iarch) , oarch_(&oarch) { deadline_.async_wait(boost::bind(&client::check_deadline, this)); deadline_.expires_from_now(boost::posix_time::seconds(30)); // Resolve the host name into an IP address. boost::asio::ip::tcp::resolver resolver(io_service); boost::asio::ip::tcp::resolver::query query(host, port); boost::asio::ip::tcp::resolver::iterator endpoint_iterator = resolver.resolve(query); // Start an asynchronous connect operation. boost::asio::async_connect(connection_.socket(), endpoint_iterator, boost::bind(&client::handle_connect, this, boost::asio::placeholders::error)); } /// Handle completion of a connect operation. void handle_connect(const boost::system::error_code& e) { if (!e) { // Successfully established connection. Start operation to read the list // of stocks. The connection::async_read() function will automatically // decode the data that is read from the underlying socket. connection_.async_read(*oarch_, boost::bind(&client::handle_read, this, boost::asio::placeholders::error)); connection_.async_write(*iarch_, boost::bind(&client::handle_write, this, boost::asio::placeholders::error)) ; } else { // An error occurred. throw sync_client_exception(e.message()); } } // Handle completion of a write operation. void handle_write(const boost::system::error_code& e) { } // Handle completion of a read operation. void handle_read(const boost::system::error_code& e) { } void check_deadline() { // Check whether the deadline has passed. We compare the deadline against // the current time since a new asynchronous operation may have moved the // deadline before this actor had a chance to run. if (deadline_.expires_at() <= deadline_timer::traits_type::now()) { // The deadline has passed. The socket is closed so that any outstanding // asynchronous operations are cancelled. connection_.socket().close(); // There is no longer an active deadline. The expiry is set to positive // infinity so that the actor takes no action until a new deadline is set. deadline_.expires_at(boost::posix_time::pos_infin); throw sync_client_exception("Time out : deadline on client!"); } // Put the actor back to sleep. deadline_.async_wait(boost::bind(&client::check_deadline, this)); } private: // The connection to the server. dsafe::sync::connection connection_; // The data received from the server. hades::archive::archive *iarch_; hades::archive::archive *oarch_; deadline_timer deadline_; }; The problem is that now the timeout expires even if the connection to the server occurs. What is wrong? My timeout should be disabled when the connection is successful! How do I get it? Only when the connection fails it should be called! Thanks for clarification
On 06/25/2013 02:51 PM, Renato Forti wrote:
void check_deadline()
The timer handle must take a boost::system::error_code as argument, and you should check this for operation_aborted.
The problem is that now the timeout expires even if the connection to the server occurs. What is wrong?
You do not call deadline_.cancel() in handle_connect().
On Tue, Jun 25, 2013 at 6:51 AM, Renato Forti
Hi All,
I have one problem, I have this class to connect to my server app:
The problem is : if my server is down, my client (session) will block on io_service.run(); the client nerves end. Then I try to add a time out:
The problem is that now the timeout expires even if the connection to the server occurs. What is wrong?
My timeout should be disabled when the connection is successful! How do I get it? Only when the connection fails it should be called!
Thanks for clarification
There is an example of the use of timeouts in the Boost Cookbook here: https://github.com/rtsuk/liaw2013/wiki/5.3-how-to-time-the-user David Sankel
participants (3)
-
Bjorn Reese
-
David Sankel
-
Renato Forti