boost::asio::read函数挂起

boost::asio::read function hanging

本文关键字:挂起 函数 asio boost read      更新时间:2023-10-16

如果有人能帮我,我无法理解boost::asio::read函数在boost-asio中是如何工作的。在boost的例子中,他们让它在收到消息之前声明缓冲区大小,这毫无意义(我如何知道在读取消息之前要读取多少字节?)

我试过这个代码,但它只是挂起

  boost::asio::io_service io_service;
  tcp::resolver resolver(io_service);
  tcp::resolver::query query(tcp::v4(), "localhost", "3000");
  tcp::resolver::iterator iterator = resolver.resolve(query);
  tcp::socket sock(io_service);
  boost::asio::connect(sock, iterator);
  cout << "read start" << endl;
  boost::system::error_code err_code;
  // Read from client.
  boost::asio::streambuf read_buffer;
  int bytes_transferred = boost::asio::read(sock, read_buffer, err_code);
  std::cout << "Read: " << make_string(read_buffer) << std::endl;
  read_buffer.consume(bytes_transferred); // Remove data that was read.

通常,您知道要从协议的定义中读取多少字节。

在相反的情况下,您必须逐个读取字节,并观察错误代码以在连接、文件等结束时停止。

Boost.Asio中的同步方法(例如read)对于简短的示例来说很好,但在实际用例中,您应该更喜欢异步版本async_read,它允许您取消或仅等待下一块数据而不阻塞程序

我也遇到了同样的问题。看起来boost::asio::read应该一直挂在那里,直到连接的客户端关闭。相反,您可以这样使用socket.read_some

using boost::asio::ip::tcp;
try {
    boost::asio::io_service io_service;
    tcp::acceptor acceptor(io_service, tcp::endpoint(tcp::v4(), 9999));
    for (;;) {
        tcp::socket socket(io_service);
        acceptor.accept(socket);
        std::string message = "server received!n";
        boost::system::error_code error_code;
        boost::asio::streambuf stream_buf;
        std::vector<char> buf(1024);
        size_t len = socket.read_some(boost::asio::buffer(buf), error_code);
        std::string received_filename(buf.begin(), buf.end());
        received_filename.resize(len);
        if (error_code) {
            std::cout << "error status: " << error_code.message() << std::endl;
        }
        boost::asio::write(socket, boost::asio::buffer(message), error_code);
        if (error_code) {
            std::cout << "error status: " << error_code.message() << std::endl;
        }
        query_database(tree, received_filename, output_folder, db_image_filenames);
    }
}
catch (std::exception& e) {
    std::cerr << e.what() << std::endl;
}

这将立即从客户端获得一条相对较短的消息。希望得到帮助。