Boost logo

Boost Users :

From: Fariya F (fariya.fatima03_at_[hidden])
Date: 2020-12-30 05:41:31


I have a server that accepts ssl connections on port 443. I am using the
boost libraries for the server implementation. Below is the code snippet:

    ssl_socket socket_;

{

   // Open the acceptor with the option to reuse the address (i.e.
 SO_REUSEADDR).
     boost::asio::ip::tcp::resolver resolver(io_service_);
     boost::asio::ip::tcp::resolver::query query(address, port);
     boost::asio::ip::tcp::endpoint endpoint = *resolver.resolve(query);
     acceptor_.open(endpoint.protocol());
     acceptor_.set_option(boost::asio::ip::tcp::acceptor::reuse_address(true));
     acceptor_.bind(endpoint);
     acceptor_.listen(1000);
      start_accept();
}
void server::start_accept() {
        new_connection_.reset(
                        new connection(io_service_,
connection_manager_, request_handler_,
                                        context_));
        acceptor_.async_accept(new_connection_->socket(),
                        boost::bind(&server::handle_accept, this,
                                        boost::asio::placeholders::error));
}
void server::handle_accept(const boost::system::error_code& e) {
        // Check whether the server was stopped by a signal before
this completion
        // handler had a chance to run.
        if (!acceptor_.is_open()) {
                return;
        } else {
                 start();
        }
         start_accept();
}

void server::start() {

        socket_.async_handshake(boost::asio::ssl::stream_base::server,
                        boost::bind(&connection::handle_handshake, this,
                                        boost::asio::placeholders::error));
        if (boost::asio::placeholders::error) {
        // printf("Error is there. Check it\n");
        }
}
void connection::handle_handshake(const boost::system::error_code& error) {

        if (!error) {
                DEBUG("async read some");
                socket_.async_read_some(boost::asio::buffer(buffer_),
                                boost::bind(&connection::handle_read,
shared_from_this(),

boost::asio::placeholders::error,

boost::asio::placeholders::bytes_transferred));
        } else {
                std::cout << "Error number: " << error.value();
                std::cout << " Error message: " << error.message();
                std::cout << " Error category: " <<
error.category().name() << std::endl;
                delete this;
        }
}

When I initiate multiple clients to connect to the server, most of the time
the connection succeeds i.e TCP handshake followed by SSL handshake
succeeds and I am able to do data transfer. However, there are times when
the TCP handshake succeeds (as seen by wireshark) but the SSL request isn't
responded to by my server. I am able to see the SSL handshake request
coming from the client onto my server, but the server doesn't respond,
neither is my handle_accept() function gets called. When I check the output
of netstat, I see a lot of data pending in the Recv-Q.

Below is the output of netstat -atn command on the server during one such
scenario:

Active Internet connections (servers and established)
Proto Recv-Q Send-Q Local Address Foreign Address State
tcp 15 0 0.0.0.0:443 0.0.0.0:* LISTEN
tcp 0 213 10.110.112.1:443 10.110.112.2:52363 ESTABLISHED
tcp 180 0 10.110.112.1:443 10.110.112.2:52624 ESTABLISHED
tcp 180 0 10.110.112.1:443 10.110.112.2:52581 ESTABLISHED
tcp 180 0 10.110.112.1:443 10.110.112.2:52646 ESTABLISHED
tcp 180 0 10.110.112.1:443 10.110.112.2:52749 ESTABLISHED
tcp 180 0 10.110.112.1:443 10.110.112.2:52824 ESTABLISHED
tcp 180 0 10.110.112.1:443 10.110.112.2:52805 ESTABLISHED
tcp 180 0 10.110.112.1:443 10.110.112.2:52645 ESTABLISHED
tcp 0 471 10.110.112.1:443 10.110.112.2:52362 ESTABLISHED
tcp 1 0 10.110.112.1:443 10.110.112.3:39129 CLOSE_WAIT
tcp 183 0 10.110.112.1:443 10.110.112.3:39130 CLOSE_WAIT
tcp 180 0 10.110.112.1:443 10.110.112.2:52595 ESTABLISHED
tcp 183 0 10.110.112.1:443 10.110.112.3:39131 CLOSE_WAIT

Upon further debugging, I see that the call to ssl socket member function
shutdown() blocks sometimes forever and sometimes for at least 5 - 10
minutes due to which no further data is taken in and the recv-q indicates
pending bytes. This is how my write handler is. Any help on where I am
going wrong would be greatly appreciated:

void connection::handle_write(const boost::system::error_code& e) {
           if (!e) {
                boost::system::error_code ec;
                socket_.shutdown(ec); //Code blocks here indefinitely
        }
}

Any reasons why the socket_.shutdown( ) blocks. How could I specify a
timeout such that the shutdown( ) returns back after some time? Any other
way of handling this? ( I know there is async_shutdown( ) but I prefer
using shutdown( ) blocking handler)

Any help would be greatly appreciated.

Regards,

Fariya



Boost-users list run by williamkempf at hotmail.com, kalb at libertysoft.com, bjorn.karlsson at readsoft.com, gregod at cs.rpi.edu, wekempf at cox.net