首页 > 解决方案 > boost::asio 将动态大小的数据传递给异步处理程序的问题

问题描述

我正在使用 boost 处理自定义 tcp 数据包。由于所有操作都是异步的,因此必须调用处理程序来处理数据。主要问题是,当编译时不知道大小时,我不知道如何将数据传递给处理程序?例如,假设您收到标头字节,解析它们告诉您正文的长度:

int length = header.body_size();

我需要以某种方式分配一个具有主体大小的数组,然后调用处理程序(这是一个类成员,而不是静态函数)并将数据传递给它。我该如何正确地做到这一点?

我尝试了不同的方法,例如但总是出现段错误,或者我必须为正文缓冲区提供固定大小,这不是我想要的。我所做的尝试可以在下面找到。

收到头信息后:

char data[header.body_size()];
boost::asio::async_read(_socket, boost::asio::buffer(data, header.body_size()),
                                    boost::bind(&TCPClient::handle_read_body, this, boost::asio::placeholders::error,
                                                boost::asio::placeholders::bytes_transferred, data));

处理程序:

void TCPClient::handle_read_body(const boost::system::error_code &error, std::size_t bytes_transferred,
                                 const char *buffer) {

    Logger::log_info("Reading body. Body size: " + std::to_string(bytes_transferred));
}

此示例引发段错误。

知道大小后如何为正文分配缓冲区?然后我怎样才能调用处理程序并传递error_code、 thebytes_transferred和 body 数据?

一个示例片段将非常感激,因为这样做的 boost-chat 示例对我来说不是很清楚。

标签: c++socketsasynchronousboostasio

解决方案


char data[header.body_size()];在 C++ 中不是标准的,一旦超出范围就会变得无效,同时async_read需要缓冲区保持活动状态,直到调用完成回调。因此,您可能应该添加一个字段来TCPClient保存待接收的数据缓冲区列表(可能是 std::vector 类型)。


推荐阅读