【问题标题】:boost::asio timeouts example - writing data is expensiveboost::asio 超时示例 - 写入数据很昂贵
【发布时间】:2011-03-14 14:41:06
【问题描述】:

boost:: asio 提供了如何使用该库来实现异步超时的示例;客户端向服务器发送服务器周期性心跳消息,服务器将心跳回显给客户端。未能在 N 秒内响应会导致断开连接。见 boost_asio/example/timeouts/server.cpp 这些示例中概述的模式将是我将很快开展的项目的一部分的一个很好的起点,但对于一个皱纹: 除了心跳之外,客户端和服务器都需要互相发送消息。 超时示例将心跳回显消息推送到队列中,随后的超时导致超时的异步处理程序实际将数据写入套接字。

在运行 io_service 的线程上无法为 socket 引入数据写入,因为它在 run() 上被阻塞。 run_once() 没有帮助,你仍然阻塞,直到有一个处理程序运行,并引入了管理 io_service 工作的复杂性。 在 asio 中,异步处理程序(写入其中之一的套接字)在运行 io_service 的线程上调用。

因此,为了随机引入消息,将要发送的数据从 io_service 线程以外的线程推送到队列中,这意味着使用互斥锁保护队列和通知计时器。然后每条消息有两个互斥锁,一个用于将数据推送到队列,一个用于将数据出列以写入套接字的处理程序。

这实际上是一个比单独的 asio 超时更普遍的问题:是否有一种模式,当 io_service 线程在 run() 上被阻塞时,可以将数据异步写入套接字,而不需要每条消息使用两个互斥锁?

【问题讨论】:

  • 我不知道为什么你需要两个互斥锁,在 io_service 已经发送消息的情况下,你不只需要一个来保护消息队列吗?至于处理程序,您可以使用相同的互斥锁来保护队列。除非你从多个线程调用 io_service::run?

标签: boost-asio


【解决方案1】:

以下内容可能很有趣:boost::asio strands 是一种同步处理程序的机制。但是,如果您从多个线程 AFAIK 调用 io_service::run,您只需要这样做。

io_service::post 方法也很有用,它允许您从调用 io_service::run 的线程执行代码。

【讨论】:

  • 感谢您的信息。在问这个问题之前,我看了一下这些; post 方法似乎没有帮助,因为处理程序的签名必须是 void handler(void);没有数据可以传入。我需要更仔细地查看 strands,但是将数据写入队列不会发生在处理程序中,那么 strands 有什么帮助?
  • 您可以使用 boost::bind (boost.org/doc/libs/release/libs/bind/bind.html) 将任意数据绑定到方法。
  • +1 io_service::postboost::bind 是去这里的方式,@user658878 你可能不需要单独的线程。
猜你喜欢
  • 2011-05-31
  • 2018-03-27
  • 1970-01-01
  • 2018-12-03
  • 2012-10-26
  • 2016-12-23
  • 1970-01-01
  • 2019-07-30
  • 1970-01-01
相关资源
最近更新 更多