【问题标题】:boost asio - exclusive binding to the network portboost asio - 独占绑定网络端口
【发布时间】:2016-03-10 13:40:33
【问题描述】:

我使用 boost asio 开发服务器应用程序。应用程序很好用。什么不起作用,是对网络端口的独占绑定。

我启动了一个应用实例——它开始监听传入的连接。

我再启动一个实例 - 它也开始侦听同一端口上的传入连接。传递给 async_accept 的处理程序未按预期调用错误。

通常我只是尝试获取端口。如果操作失败 - 端口正在使用中。对于 Asio,这种方法不起作用。如何检查端口的可用性?

void TcpServerFactory::acceptConnectionsOnPort(int serverPort,
                                               boost::shared_ptr<TcpConfigServerReceiver> tcpConfig,
                                               boost::function<void(boost::shared_ptr<TcpServer>)> onSuccessfullyConnectedHandler)
{
    // todo check is port not busy
    FORMATTED_LOG(this->_log, info) << "Start to accept connections on port " << serverPort;
    auto endpoint = boost::asio::ip::tcp::endpoint(boost::asio::ip::tcp::v4(), serverPort);
    boost::shared_ptr<boost::asio::ip::tcp::acceptor> tcpAcceptor(new boost::asio::ip::tcp::acceptor(this->_ioService, endpoint));

    this->acceptConnections(tcpAcceptor, tcpConfig, onSuccessfullyConnectedHandler);
}

void TcpServerFactory::acceptConnections(boost::shared_ptr<boost::asio::ip::tcp::acceptor> tcpAcceptor,
                                         boost::shared_ptr<TcpConfigServerReceiver> tcpConfig,
                                         boost::function<void(boost::shared_ptr<TcpServer>)> onSuccessfullyConnectedHandler)
{
    boost::shared_ptr<boost::asio::ip::tcp::socket> tcpSocket(new boost::asio::ip::tcp::socket(this->_ioService));
    boost::function<void(const boost::system::error_code &)> onAcceptOperationCompletedHandler =
        boost::bind(&TcpServerFactory::onAcceptOperationCompleted, this->downcasted_shared_from_this<TcpServerFactory>(),
                    _1, tcpAcceptor, tcpSocket, tcpConfig, onSuccessfullyConnectedHandler);

    tcpAcceptor.get()->async_accept(*tcpSocket, onAcceptOperationCompletedHandler);
}

void TcpServerFactory::onAcceptOperationCompleted(const boost::system::error_code & err,
                                                  boost::shared_ptr<boost::asio::ip::tcp::acceptor> tcpAcceptor,
                                                  boost::shared_ptr<boost::asio::ip::tcp::socket> tcpSocket,
                                                  boost::shared_ptr<TcpConfigServerReceiver> tcpConfig,
                                                  boost::function<void(boost::shared_ptr<TcpServer>)> onSuccessfullyConnectedHandler)
{
    if (err)
    {
        FORMATTED_LOG(this->_log, info) << "Failed to accept connections on port " << tcpAcceptor->local_endpoint().port() << "due to error " << BOOST_ERROR_TO_STREAM(err);
        return;
    }
    this->acceptConnections(tcpAcceptor, tcpConfig, onSuccessfullyConnectedHandler);
    this->onConnectionEstablished(tcpSocket, tcpConfig, onSuccessfullyConnectedHandler);
}

更新

我尝试在一系列命令上替换接受器的构造函数。我预计会在tcpAcceptor-&gt;bind() 上引发异常,但这并没有发生。

// boost::shared_ptr<boost::asio::ip::tcp::acceptor> tcpAcceptor(new boost::asio::ip::tcp::acceptor(this->_ioService, endpoint));


boost::shared_ptr<boost::asio::ip::tcp::acceptor> tcpAcceptor(new boost::asio::ip::tcp::acceptor(this->_ioService));
tcpAcceptor->open(endpoint.protocol());
tcpAcceptor->set_option(boost::asio::socket_base::reuse_address(true));
tcpAcceptor->bind(endpoint);
boost::system::error_code err;
tcpAcceptor->listen(boost::asio::socket_base::max_connections, err);

【问题讨论】:

    标签: boost boost-asio


    【解决方案1】:

    reuse_address 不应该这样做。其含义是在端口被释放后避免“等待”间隔。

    【讨论】:

    • 感谢您的澄清。我误解了有关reuse_address 的文档。但是如何使用 Asio 检查端口的可用性?
    • @VictorMezrin 你会在尝试 bind() 时得到asio::error::address_in_use 异常。
    • 我使用这个acceptor的构造函数:http://goo.gl/QLoR2L(重载3)。根据内部文档,它调用acceptor.bind(),但未引发异常。我试图用一系列命令替换构造函数(查看问题的更新) - 这也不起作用:(
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2018-03-07
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-04-22
    • 2017-11-30
    • 1970-01-01
    相关资源
    最近更新 更多