【问题标题】:boost signal double free?升压信号双倍免费?
【发布时间】:2009-08-20 12:57:20
【问题描述】:

我正在尝试调试某种内存访问错误,我认为这是双重释放。代码太复杂,不能贴出来,不过我可以试着描述一下。

基本上,我有两个线程。创建工作线程时,它会实例化一个new boost::signal 对象,并将其存储在shared_ptr 中。然后父进程向线程查询信号,父进程connect()s 将shared_ptr 信号发送给处理函数。

这一切都有效,直到线程完成并尝试清理为止。这是调用堆栈的一个片段,希望有人能看到我错过的东西。

ntdll.dll!7c90120e()    
ntdll.dll!7c96e139()    
ntdll.dll!7c96e576()    
ntdll.dll!7c9622e8()    
kernel32.dll!7c85f8d7()     
Worker.dll!_CrtIsValidHeapPointer(const void * pUserData=0x01788aa8)  Line 1807 C
Worker.dll!_free_dbg_lk(void * pUserData=0x01788aa8, int nBlockUse=1)  Line 1132 + 0x9  C
Worker.dll!_free_dbg(void * pUserData=0x01788aa8, int nBlockUse=1)  Line 1070 + 0xd C
Worker.dll!operator delete(void * pUserData=0x01788aa8)  Line 54 + 0x10 C++
Worker.dll!std::allocator<std::_List_nod<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >::_Node>::deallocate(std::_List_nod<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >::_Node * _Ptr=0x01788aa8, unsigned int __formal=1)  Line 132 + 0x9  C++
Worker.dll!std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >::clear()  Line 622 C++
Worker.dll!std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >::_Tidy()  Line 931 C++
Worker.dll!std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >::~list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >()  Line 366 C++
Worker.dll!std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > >::~pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > >()  + 0x2e   C++
Worker.dll!std::_Tree_nod<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::_Node::~_Node()  + 0x12  C++
Worker.dll!std::_Tree_nod<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::_Node::`scalar deleting destructor'()  + 0xf C++
Worker.dll!std::_Destroy<std::_Tree_nod<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::_Node>(std::_Tree_nod<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::_Node * _Ptr=0x013a3008)  Line 50   C++
Worker.dll!std::allocator<std::_Tree_nod<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::_Node>::destroy(std::_Tree_nod<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::_Node * _Ptr=0x013a3008)  Line 152 + 0x9  C++
Worker.dll!std::_Tree<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::_Erase(std::_Tree_nod<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::_Node * _Rootnode=0x013a3008)  Line 896   C++
Worker.dll!std::_Tree<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::_Erase(std::_Tree_nod<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::_Node * _Rootnode=0x013a2f48)  Line 894   C++
Worker.dll!std::_Tree<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::clear()  Line 782    C++
Worker.dll!std::_Tree<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::erase(std::_Tree<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::iterator _First={...}, std::_Tree<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::iterator _Last={...})  Line 754 C++
Worker.dll!std::_Tree<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::_Tidy()  Line 1144   C++
Worker.dll!std::_Tree<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >::~_Tree<std::_Tmap_traits<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > >,0> >()  Line 393   C++
Worker.dll!std::map<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > > >::~map<boost::signals::detail::stored_group,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> >,boost::function2<bool,boost::signals::detail::stored_group,boost::signals::detail::stored_group,std::allocator<boost::function_base> >,std::allocator<std::pair<boost::signals::detail::stored_group const ,std::list<boost::signals::detail::connection_slot_pair,std::allocator<boost::signals::detail::connection_slot_pair> > > > >()  + 0xf    C++
Worker.dll!boost::signals::detail::named_slot_map::~named_slot_map()  + 0xf C++
Worker.dll!boost::signals::detail::signal_base_impl::~signal_base_impl()  Line 33 + 0x1d    C++
Worker.dll!boost::signals::detail::signal_base_impl::`scalar deleting destructor'()  + 0xf  C++
Worker.dll!boost::checked_delete<boost::signals::detail::signal_base_impl>(boost::signals::detail::signal_base_impl * x=0x013a2d98)  Line 34 + 0x1c C++
Worker.dll!boost::detail::sp_counted_impl_p<boost::signals::detail::signal_base_impl>::dispose()  Line 79 + 0xc C++
Worker.dll!boost::detail::sp_counted_base::release()  Line 102 + 0xd    C++
Worker.dll!boost::detail::shared_count::~shared_count()  Line 209   C++
Worker.dll!boost::shared_ptr<boost::signals::detail::signal_base_impl>::~shared_ptr<boost::signals::detail::signal_base_impl>()  + 0x12 C++
Worker.dll!boost::signals::detail::signal_base::~signal_base()  Line 184 + 0x8  C++
Worker.dll!boost::signal2<void,enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >,boost::last_value<void>,int,std::less<int>,boost::function<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),std::allocator<void> > >::~signal2<void,enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >,boost::last_value<void>,int,std::less<int>,boost::function<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),std::allocator<void> > >()  + 0x77 C++
Worker.dll!boost::signal<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),boost::last_value<void>,int,std::less<int>,boost::function<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),std::allocator<void> > >::~signal<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),boost::last_value<void>,int,std::less<int>,boost::function<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),std::allocator<void> > >()  + 0x2b C++
Worker.dll!boost::signal<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),boost::last_value<void>,int,std::less<int>,boost::function<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),std::allocator<void> > >::`scalar deleting destructor'()  + 0x2b  C++
Worker.dll!boost::checked_delete<boost::signal<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),boost::last_value<void>,int,std::less<int>,boost::function<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),std::allocator<void> > > >(boost::signal<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),boost::last_value<void>,int,std::less<int>,boost::function<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),std::allocator<void> > > * x=0x013a2cf8)  Line 34 + 0x2b  C++
Worker.dll!boost::detail::sp_counted_impl_p<boost::signal<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),boost::last_value<void>,int,std::less<int>,boost::function<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),std::allocator<void> > > >::dispose()  Line 79 + 0xc C++
Worker.dll!boost::detail::sp_counted_base::release()  Line 102 + 0xd    C++
Worker.dll!boost::detail::shared_count::~shared_count()  Line 209   C++
Worker.dll!boost::shared_ptr<boost::signal<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),boost::last_value<void>,int,std::less<int>,boost::function<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),std::allocator<void> > > >::~shared_ptr<boost::signal<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),boost::last_value<void>,int,std::less<int>,boost::function<void __cdecl(enum signal_e,std::basic_string<char,std::char_traits<char>,std::allocator<char> >),std::allocator<void> > > >()  + 0x2e C++
Worker.dll!CWorker::~CWorker()  Line 77 + 0x24  C++
Worker.dll!CWorker::`scalar deleting destructor'()  + 0x2b  C++
Worker.dll!boost::checked_delete<CSubclass>(CSubclass* x=0x013a2ab0)  Line 34 + 0x32    C++
Worker.dll!boost::detail::sp_counted_impl_p<CSubclass>::dispose()  Line 79 + 0xc    C++
Parent.exe!boost::detail::sp_counted_base::release()  Line 102 + 0xd    C++
Parent.exe!boost::detail::shared_count::~shared_count()  Line 209   C++
Parent.exe!boost::shared_ptr<void>::~shared_ptr<void>()  + 0x19 C++
Parent.exe!CWorker::~CWorker()  Line 33 + 0x20  C++

任何建议将不胜感激。我已经研究了几天,但无法弄清楚问题所在。

【问题讨论】:

    标签: c++ boost boost-signals


    【解决方案1】:

    我在一两年前遇到了这个问题,IIRC,这是由于没有使用 boost::signals::connection objects 明确管理连接造成的。

    【讨论】:

    • 听起来很合理,我会进一步研究。
    • 你也可以通过继承 boost::signals::trackable 来管理它。
    【解决方案2】:

    我知道这确实没有帮助,但请投资像 Purify 这样的工具。在追踪内存泄漏方面,它真的很值得。它现在可能已经收回了成本。

    【讨论】:

    • 是的,这很有价值,但当然,我不是做出这样决定的人。 :-)
    • 建议零售价 870.00 美元 @ Ibm.com:任何 C++ 商店都不应该没有这个工具的副本,就像任何 Java 商店都不应该没有 YourKit 的副本,恕我直言。
    【解决方案3】:

    Re:Purify——它是一个很棒的工具,尽管有一些明显的限制(基本上它需要检测应用程序使用的每个共享库,至少在 Linux 上是这样)。

    如果您买不起 Purify 和/或对其限制有疑问,请尝试使用 valgrind (valgrind.org)。它使用不同的方法来解决问题(即,它运行模拟机器,因此您不需要检测任何东西 - 哦,它可以是 sssslllllooooooowwwwwww)

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2017-04-07
      • 1970-01-01
      • 2013-02-01
      • 1970-01-01
      • 2014-04-29
      • 1970-01-01
      • 2021-10-23
      相关资源
      最近更新 更多