当我在我的方法SendMessageAgain调用deadline_timer::async_wait ,有时会引发段错误。 它可以通过以下两种方式之一发生: 我在下面包括了回溯。 它似乎是随机的,这使我以某种方式考虑了比赛条件。 我有一个带有io_service对象ioService的类,以及多个线程,每个线程都有与ioService挂钩的ioService 在调用async_wait之前是否可能需要锁定ioService 我以为它可以解决这个问题。

也许它与计时器滴答声中被中断的任何代码有关。 当同时执行其他代码时,设置截止期限计时器的正确方法是什么?

我在SendMessageAgain中使用的代码是

void Node::SendMessageAgain(unsigned long seqNum) {
  // figure out if and what to send (using object fields)
  if (should_send_again) {
    Send(...);
    timer->expires_from_now(INTERVAL);
    timer->async_wait(bind(&Node::SendMessageAgain, this, seqNum));
  }
}
#0  0x08060609 in boost::asio::detail::deadline_timer_service<boost::asio::time_traits<boost::posix_time::ptime> >::async_wait<boost::_bi::bind_t<void, boost::_mfi::mf1<void, Node, unsigned long>, boost::_bi::list2<boost::_bi::value<Node*>, boost::_bi::value<unsigned long> > > > (this=0x14, impl=..., handler=...)
    at /usr/include/boost/asio/detail/deadline_timer_service.hpp:170
#1  0x0805e2e7 in boost::asio::deadline_timer_service<boost::posix_time::ptime, boost::asio::time_traits<boost::posix_time::ptime> >::async_wait<boost::_bi::bind_t<void, boost::_mfi::mf1<void, Node, unsigned long>, boost::_bi::list2<boost::_bi::value<Node*>, boost::_bi::value<unsigned long> > > > (this=0x0, impl=..., 
    handler=...) at /usr/include/boost/asio/deadline_timer_service.hpp:135
#2  0x0805bcbb in boost::asio::basic_deadline_timer<boost::posix_time::ptime, boost::asio::time_traits<boost::posix_time::ptime>, boost::asio::deadline_timer_service<boost::posix_time::ptime, boost::asio::time_traits<boost::posix_time::ptime> > >::async_wait<boost::_bi::bind_t<void, boost::_mfi::mf1<void, Node, unsigned long>, boost::_bi::list2<boost::_bi::value<Node*>, boost::_bi::value<unsigned long> > > > (this=0x807fc50, handler=...)
    at /usr/include/boost/asio/basic_deadline_timer.hpp:435
#3  0x080555a2 in Node::SendMessageAgain (this=0xbfffefdc, seqNum=8)
    at node.cpp:147
#0  __pthread_mutex_lock (mutex=0x2f200c4) at pthread_mutex_lock.c:50
#1  0x08056c79 in boost::asio::detail::posix_mutex::lock (this=0x2f200c4)
    at /usr/include/boost/asio/detail/posix_mutex.hpp:52
#2  0x0805a036 in boost::asio::detail::scoped_lock<boost::asio::detail::posix_mutex>::scoped_lock (this=0xbfffeb04, m=...)
    at /usr/include/boost/asio/detail/scoped_lock.hpp:36
#3  0x08061dd0 in boost::asio::detail::epoll_reactor::schedule_timer<boost::asio::time_traits<boost::posix_time::ptime> > (this=0x2f200ac, queue=..., 
    time=..., timer=..., op=0x807fca0)
    at /usr/include/boost/asio/detail/impl/epoll_reactor.hpp:43
#4  0x0806063a in boost::asio::detail::deadline_timer_service<boost::asio::time_traits<boost::posix_time::ptime> >::async_wait<boost::_bi::bind_t<void, boost::_mfi::mf1<void, Node, unsigned long>, boost::_bi::list2<boost::_bi::value<Node*>, boost::_bi::value<unsigned long> > > > (this=0xb6b005fc, impl=..., 
    handler=...)
    at /usr/include/boost/asio/detail/deadline_timer_service.hpp:170
#5  0x0805e2fd in boost::asio::deadline_timer_service<boost::posix_time::ptime, boost::asio::time_traits<boost::posix_time::ptime> >::async_wait<boost::_bi::bind_t<void, boost::_mfi::mf1<void, Node, unsigned long>, boost::_bi::list2<boost::_bi::value<Node*>, boost::_bi::value<unsigned long> > > > (this=0xb6b005e8, 
    impl=..., handler=...)
    at /usr/include/boost/asio/deadline_timer_service.hpp:135
#6  0x0805bcd1 in boost::asio::basic_deadline_timer<boost::posix_time::ptime, bo---Type <return> to continue, or q <return> to quit---
ost::asio::time_traits<boost::posix_time::ptime>, boost::asio::deadline_timer_service<boost::posix_time::ptime, boost::asio::time_traits<boost::posix_time::ptime> > >::async_wait<boost::_bi::bind_t<void, boost::_mfi::mf1<void, Node, unsigned long>, boost::_bi::list2<boost::_bi::value<Node*>, boost::_bi::value<unsigned long> > > > (this=0xb6b005a0, handler=...)
    at /usr/include/boost/asio/basic_deadline_timer.hpp:435
#7  0x080555a7 in Node::SendMessageAgain (this=0xbfffefdc, seqNum=9)
    at node.cpp:148

===============>>#1 票数:2 已采纳

好吧,它是固定的。 正如Sam所建议的那样,这是对象生命周期的问题,尽管Node却不是。 我在Node拥有的对象中有一个计时器。 我的代码中有一个竞争条件,我要在关键部分之外重置计时器,并且在关键部分结束和计时器重置之间其所有者被销毁。 我只是扩展了关键部分,并对其进行了修复。

我不确定为什么段错误会在async_wait如此低地表现出来,因为回调(以及与this指针相关联)属于Node ,而Node仍然存在。

===============>>#2 票数:0

坏:

timer->async_wait(bind(&Node::SendMessageAgain, this, seqNum, _1));

好:

timer->async_wait(bind(&Node::SendMessageAgain, shared_from_this(), seqNum, _1));

让节点扩展enable_shared_from_this

class Node : public boost::enable_shared_from_this<Node>

如果这是由于您的Node被销毁而仍在为其安排回调的话,则可以解决此问题。

  ask by Nick translate from so

未解决问题?本站智能推荐:

1回复

Boost.Asio:异步操作超时

我的程序充当客户端可以连接的服务器。 一旦客户端连接,他将每隔约5秒从服务器获得更新。 这是每5秒调用一次的write函数,用于将新数据发送到客户端: 如果写操作中存在错误,则服务器和客户端之间的连接将关闭,并且所有异步操作都将被清除( this->socket_.lowest
1回复

来自boost Asio deadline_timer的多个async_wait

是否可以在同一个boost :: asio :: deadline_timer上多次调用async_wait? 我的意思是如下: 这是否确保将调用这两个函数? 这是否确保按此顺序调用这两个函数? 如果没有,任何想法如何在定时器超时时连续调用f1和f2? (我不关心在f1和
1回复

boost :: asio :: deadline_timer :: async_wait不触发回调

我有一个在线程中运行的boost io_service ,我想在客户端发生某个事件之后6秒钟在该线程中触发一个回调,如果该客户端已经在运行,请重置该计时器。 我为每个客户端维护了一个带有计时器的unordered_map<string, shared_ptr<deadline_
2回复

boost :: deadline_timer :: async_wait不是异步的

我执行一个简单的示例作为测试,我想在5秒钟后执行一个简单的操作。 我正在使用带有async_wait的boost :: deadline_timer,但async_wait不会异步等待...这是代码: 这是输出: 发生错误是因为计时器必须在后台等待,然后才能继续执行下一条指令“
2回复

使用boost :: asio :: async_wait_until和boost :: asio :: streambuf

我有一个当前正在开发的应用程序,用于使用串行通信与设备进行通信。 为此,我使用了增强库basic_serial_port。 现在,我只是尝试从设备读取数据,并且正在使用async_wait_until函数,再加上deadline_timer async_wait类中的async_wait 。
3回复

提升asio deadline_timer

我期待下面的代码打印Hello,world! 每5秒钟,但会发生的是程序暂停5秒钟,然后一遍又一遍地打印消息而没有后续暂停。 我错过了什么? 编辑以在下面添加工作代码。 多谢你们。
2回复

提升ASIO - 什么是异步

我一直在做很多阅读,但我无法理解Boost ASIO中同步和异步调用之间的区别:它们是什么,它们是如何工作的,以及为什么选择一个而不是另一个。 我的模型是一个服务器,它接受连接并将新连接附加到列表。 一个不同的线程在列表上循环,并在每个已注册的连接数据可用时发送它们。 每次写操作都应该
2回复

boost :: asio :: async_read在换行符上返回文件结束错误

我正在尝试使用带有超时的async_read和async_write向服务器发出简单的tcp请求。 问题是async_read在尝试读取直到传输结束时给出错误,在第一个'\\ n'上它返回错误(文件末尾)。 当逐行读取字符串时(当eots-> at(last_request)=
2回复

Boost asio,shared_from_this()错误R6010和async_read()eof

我正在尝试与boost asio聊天,以官方示例为参考。 但是我实际上在async_read上遇到两个问题,首先,为什么我有一个EoF(文件结尾)并且我的连接(和应用程序)在客户端中关闭得这么快? 然后我在ChatParticipant的async_read中遇到了一个问题:如果我将“
1回复

删除后async_write会导致分段错误吗?

我正在使用Boost通过async_write通过TCP发送数据: std::shared_ptr<std::vector<std::string>::iterator> iter = std::make_shared<std::vector<std::s