1

我有以下一点 ASIO 代码,它同步读取 UDP 数据包。问题是,如果在给定的时间范围(30 秒)内没有给定大小的数据包到达,我希望 recieve_from 函数返回某种错误以指定超时。

for (;;)
{
  boost::array<char, 1000> recv_buf;
  udp::endpoint remote_endpoint;
  asio::error_code error;

  socket.receive_from(asio::buffer(recv_buf),   // <-- require timeout
      remote_endpoint, 0, error);

  if (error && error != asio::error::message_size)
    throw asio::system_error(error);

  std::string message = make_daytime_string();

  asio::error_code ignored_error;
  socket.send_to(asio::buffer(message),
      remote_endpoint, 0, ignored_error);
}

查看文档,非面向 UDP 的调用支持超时机制。

在 ASIO 中同步 UDP 调用超时的正确方法是什么(如果可能,也可以移植)?

4

1 回答 1

0

据我所知,这是不可能的。通过运行同步receive_from,您已经阻止了recvmsg来自#include <sys/socket.h>.

随着可移植性的发展,我不能代表 Windows,但 linux/bsd C 风格的解决方案看起来像这样:

void SignalHandler(int signal) {
  // do what you need to do, possibly informing about timeout and calling exit()
}

...
struct sigaction signal_action;
signal_action.sa_flags = 0;
sigemptyset(&signal_action.sa_mask);
signal_action.sa_handler = SignalHandler;
if (sigaction(SIGALRM, &signal_action, NULL) == -1) {
  // handle error
}
...
int timeout_in_seconds = 5;
alarm(timeout_in_seconds);
...
socket.receive_from(asio::buffer(recv_buf), remote_endpoint, 0, error);
...
alarm(0);

如果这根本不可行,我建议完全异步并在boost::asio::io_service.

于 2017-08-18T16:07:28.157 回答