Boost asio在一段时间后停止处理

时间:2015-08-11 11:05:51

标签: c++ boost network-programming boost-asio

我有一个服务器应用程序,它使用boost.asio框架。应用程序逻辑很简单 - 它在几个端口上侦听传入连接,接受它,进行一些处理并关闭连接。当然,多个客户端允许同时连接到服务器。我使用异步方法接受连接读写数据。问题是,在某些时候,io_service只是停止处理处理程序。

让我更详细地描述症状。出现问题后,应用程序继续侦听指定的端口,netstat命令可以验证。客户端可以建立与服务器的连接,但不会调用单个处理程序(Server :: Session)。

以下是接受连接的代码:

void Server::StartAccept()
{
     socket_ptr sock(new boost::asio::ip::tcp::socket(ioService_));
     acceptor_.async_accept(*sock, boost::bind(&Server::Session, shared_from_this(), sock, boost::asio::placeholders::error));
}

void Server::Session(socket_ptr sock, const boost::system::error_code& error)
{
     StartAccept();
     if(error)
     {
          boost::system::error_code ec;
          sock->shutdown(boost::asio::ip::tcp::socket::shutdown_both, ec);
          sock->close(ec);
          return;
     }

     //Processing...
}

以下是启动服务器的代码:

void run_service()
{
     for (;;)
     {
          try
          {
               io_service.run();
               break;
          }
          catch (...)
          {
          }
     }
}

boost::thread_group threads;

for ( int i = 0; i < size; ++i)
    threads.create_thread(run_service);

threads.join_all();

我发现了,如果我替换行

io_service.run();

while (!io_service.stopped())
    io_service.run_once();

这个循环会在出现错误时卡住,并且run_once函数永远不会返回。

我对可能发生这种情况的假设:

  • 一个被称为处理程序的处理程序永远不会返回。
  • 这是boost内部的某种死锁(因为我没有做任何锁定)。

问题是:

  • 这种奇怪的行为还有什么其他原因?
  • 解决这个问题的最佳方法是什么?
  • 如何判断run_once函数在卡住之前调用哪个处理程序?

1 个答案:

答案 0 :(得分:0)

问题在于处理程序,它等待另一个网络活动完成。这项活动没有超时,在某些情况下持续了很长时间。感谢您的评论。定义BOOST_ASIO_ENABLE_HANDLER_TRACKING是检测问题的非常好的一步。