Opened 7 years ago

Closed 6 years ago

#11275 closed Support Requests (worksforme)

Deadlock when destroying continuation future

Reported by: Konrad Zemek <konrad.zemek@…> Owned by: viboes
Milestone: Component: thread
Version: Boost 1.58.0 Severity: Problem
Keywords: continuation deadlock destructor Cc:

Description

I've stumbled upon a deadlock somewhere in continuation logic. I think the trace below will show it clearly. Basically, the future's destructor waits on lock that was already locked earlier in the callstack:

In the continuation sequence:

#22 0x0000000000505283 in boost::detail::shared_state_base::do_continuation (this=0x18979d0, lock=...)
    at /usr/include/boost/thread/future.hpp:239
239	                  }
(gdb) print lock
$2 = (boost::unique_lock<boost::mutex> &) @0x7f6e62783520: {m = 0x1897a10, is_locked = true}

Later during destruction:

#7  0x0000000000505083 in boost::detail::shared_state_base::dec (this=0x18979d0) at /usr/include/boost/thread/future.hpp:197
197	            void dec() { boost::unique_lock<boost::mutex> lk(this->mutex); dec(lk); }
(gdb) print lk
$4 = {m = 0x1897a10, is_locked = false}

Following is the trace from GDB. I attach my version of future.hpp for line number reference. It's the version from 71d9a0a merged with boost-1.58 tag.

Thread 2 (Thread 0x7f6e62786700 (LWP 12760)):
#0  __lll_lock_wait () at ../nptl/sysdeps/unix/sysv/linux/x86_64/lowlevellock.S:135
#1  0x00007f6e64b8156a in _L_lock_913 () from /lib/x86_64-linux-gnu/libpthread.so.0
#2  0x00007f6e64b81390 in __GI___pthread_mutex_lock (mutex=0x1897a10) at ../nptl/pthread_mutex_lock.c:79
#3  0x000000000050236a in pthread_mutex_lock (m=0x1897a10) at /usr/include/boost/thread/pthread/mutex.hpp:62
#4  boost::mutex::lock (this=0x1897a10) at /usr/include/boost/thread/pthread/mutex.hpp:116
#5  0x000000000050f881 in boost::unique_lock<boost::mutex>::lock (this=0x7f6e627831f0)
    at /usr/include/boost/thread/lock_types.hpp:346
#6  0x000000000050f9e9 in boost::unique_lock<boost::mutex>::unique_lock (this=0x7f6e627831f0, m_=...)
    at /usr/include/boost/thread/lock_types.hpp:124
#7  0x0000000000505083 in boost::detail::shared_state_base::dec (this=0x18979d0) at /usr/include/boost/thread/future.hpp:197
#8  0x000000000052850e in boost::detail::basic_future<boost::future<std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > > >::~basic_future (this=0x1897c58, __in_chrg=<optimized out>)
    at /usr/include/boost/thread/future.hpp:1212
#9  0x000000000051f46e in boost::future<boost::future<std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > > >::~future (this=0x1897c58, __in_chrg=<optimized out>) at /usr/include/boost/thread/future.hpp:1822
#10 0x0000000000534fbc in boost::detail::future_unwrap_shared_state<boost::future<boost::future<std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > > >, std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > >::~future_unwrap_shared_state (this=0x1897b40, __in_chrg=<optimized out>)
    at /usr/include/boost/thread/future.hpp:5043
#11 0x0000000000534ff8 in boost::detail::future_unwrap_shared_state<boost::future<boost::future<std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > > >, std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > >::~future_unwrap_shared_state (this=0x1897b40, __in_chrg=<optimized out>)
    at /usr/include/boost/thread/future.hpp:5043
#12 0x0000000000535030 in boost::checked_delete<boost::detail::future_unwrap_shared_state<boost::future<boost::future<std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > > >, std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > > > (x=0x1897b40)
    at /usr/include/boost/core/checked_delete.hpp:34
#13 0x00000000005382ee in boost::detail::sp_counted_impl_p<boost::detail::future_unwrap_shared_state<boost::future<boost::future<std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > > >, std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > > >::dispose (this=0x1897880)
    at /usr/include/boost/smart_ptr/detail/sp_counted_impl.hpp:78
#14 0x00000000005017e2 in boost::detail::sp_counted_base::release (this=0x1897880)
    at /usr/include/boost/smart_ptr/detail/sp_counted_base_gcc_x86.hpp:146
#15 0x00000000005018a5 in boost::detail::shared_count::~shared_count (this=0x7f6e5c0008c8, __in_chrg=<optimized out>)
    at /usr/include/boost/smart_ptr/detail/shared_count.hpp:443
#16 0x0000000000505114 in boost::shared_ptr<boost::detail::shared_state_base>::~shared_ptr (this=0x7f6e5c0008c0, 
    __in_chrg=<optimized out>) at /usr/include/boost/smart_ptr/shared_ptr.hpp:323
#17 0x000000000052f13e in std::_Destroy<boost::shared_ptr<boost::detail::shared_state_base> > (__pointer=0x7f6e5c0008c0)
    at /usr/include/c++/4.9/bits/stl_construct.h:93
#18 0x0000000000529d5d in std::_Destroy_aux<false>::__destroy<boost::shared_ptr<boost::detail::shared_state_base>*> (
    __first=0x7f6e5c0008c0, __last=0x7f6e5c0008d0) at /usr/include/c++/4.9/bits/stl_construct.h:103
#19 0x00000000005228f3 in std::_Destroy<boost::shared_ptr<boost::detail::shared_state_base>*> (__first=0x7f6e5c0008c0, 
    __last=0x7f6e5c0008d0) at /usr/include/c++/4.9/bits/stl_construct.h:126
#20 0x0000000000516107 in std::_Destroy<boost::shared_ptr<boost::detail::shared_state_base>*, boost::shared_ptr<boost::detail::shared_state_base> > (__first=0x7f6e5c0008c0, __last=0x7f6e5c0008d0) at /usr/include/c++/4.9/bits/stl_construct.h:151
#21 0x000000000050d24f in std::vector<boost::shared_ptr<boost::detail::shared_state_base>, std::allocator<boost::shared_ptr<boost::detail::shared_state_base> > >::~vector (this=0x7f6e62783450, __in_chrg=<optimized out>)
    at /usr/include/c++/4.9/bits/stl_vector.h:424
#22 0x0000000000505283 in boost::detail::shared_state_base::do_continuation (this=0x18979d0, lock=...)
    at /usr/include/boost/thread/future.hpp:239
#23 0x0000000000505412 in boost::detail::shared_state_base::mark_finished_internal (this=0x18979d0, lock=...)
    at /usr/include/boost/thread/future.hpp:265
#24 0x0000000000544a2d in boost::detail::shared_state<boost::future<std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > > >::mark_finished_with_result_internal(boost::future<std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > >&&, boost::unique_lock<boost::mutex>&) (this=0x18979d0, 
    result_=<unknown type in /home/kzemek/plgrid/helpers/debug/test/unit/inbox_test, CU 0xa555, DIE 0x4091f>, lock=...)
    at /usr/include/boost/thread/future.hpp:526
#25 0x000000000054499f in boost::detail::shared_state<boost::future<std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > > >::mark_finished_with_result(boost::future<std::unique_ptr<one::clproto::ServerMessage, std::default_delete<one::clproto::ServerMessage> > >&&) (this=0x18979d0, 
---Type <return> to continue, or q <return> to quit---
    result_=<unknown type in /home/kzemek/plgrid/helpers/debug/test/unit/inbox_test, CU 0xa555, DIE 0x4091f>)
    at /usr/include/boost/thread/future.hpp:554
#26 0x00000000005448be in _ZN5boost6detail41future_executor_continuation_shared_stateINS_9executors17basic_thread_poolENS_6futureIvEENS4_ISt10unique_ptrIN3one7clproto13ServerMessageESt14default_deleteIS9_EEEEZNS7_13communication6layers5InboxI10LowerLayerE11communicateES6_INS8_13ClientMessageESA_ISJ_EEiEUlT_E_E3runENS_10shared_ptrINS0_17shared_state_baseEEE (that_=...)
    at /usr/include/boost/thread/future.hpp:4303
#27 0x0000000000544738 in _ZN5boost6detail6run_itINS0_41future_executor_continuation_shared_stateINS_9executors17basic_thread_poolENS_6futureIvEENS5_ISt10unique_ptrIN3one7clproto13ServerMessageESt14default_deleteISA_EEEEZNS8_13communication6layers5InboxI10LowerLayerE11communicateES7_INS9_13ClientMessageESB_ISK_EEiEUlT_E_EEEclEv (this=0x18978a8)
    at /usr/include/boost/thread/future.hpp:4274
#28 0x00000000005445ba in _ZN5boost6detail16nullary_functionIFvvEE9impl_typeINS0_6run_itINS0_41future_executor_continuation_shared_stateINS_9executors17basic_thread_poolENS_6futureIvEENS9_ISt10unique_ptrIN3one7clproto13ServerMessageESt14default_deleteISE_EEEEZNSC_13communication6layers5InboxI10LowerLayerE11communicateESB_INSD_13ClientMessageESF_ISO_EEiEUlT_E_EEEEE4callEv (
    this=0x18978a0) at /usr/include/boost/thread/detail/nullary_function.hpp:52
#29 0x0000000000507245 in boost::detail::nullary_function<void ()>::operator()() (this=0x7f6e62783690)
    at /usr/include/boost/thread/detail/nullary_function.hpp:125
#30 0x00000000005072a3 in boost::executors::basic_thread_pool::worker_thread (this=0x1894ba0)
    at /usr/include/boost/thread/executors/basic_thread_pool.hpp:91
#31 0x000000000053f129 in boost::detail::invoke<void (boost::executors::basic_thread_pool::*)(), boost::executors::basic_thread_pool<>*>(void (boost::executors::basic_thread_pool::*&&)(), boost::executors::basic_thread_pool<>*&&, (boost::executors::basic_thread_pool<>*&&)...) (
    f=<unknown type in /home/kzemek/plgrid/helpers/debug/test/unit/inbox_test, CU 0xa555, DIE 0xa1b40>, 
    a0=<unknown type in /home/kzemek/plgrid/helpers/debug/test/unit/inbox_test, CU 0xa555, DIE 0xa1b45>)
    at /usr/include/boost/thread/detail/invoke.hpp:77
#32 0x000000000053c705 in boost::detail::thread_data<void (boost::executors::basic_thread_pool::*)(), boost::executors::basic_thread_pool*>::run2<1ul> (this=0x1894f20) at /usr/include/boost/thread/detail/thread.hpp:75
#33 0x0000000000538e5a in boost::detail::thread_data<void (boost::executors::basic_thread_pool::*)(), boost::executors::basic_thread_pool*>::run (this=0x1894f20) at /usr/include/boost/thread/detail/thread.hpp:81
#34 0x00007f6e64da5d8a in ?? () from /usr/lib/x86_64-linux-gnu/libboost_thread.so.1.58.0
#35 0x00007f6e64b7f0a5 in start_thread (arg=0x7f6e62786700) at pthread_create.c:309
#36 0x00007f6e63e1ecfd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:111

Attachments (1)

future.hpp (182.8 KB ) - added by Konrad Zemek <konrad.zemek@…> 7 years ago.

Download all attachments as: .zip

Change History (11)

by Konrad Zemek <konrad.zemek@…>, 7 years ago

Attachment: future.hpp added

in reply to:  description comment:1 by Konrad Zemek <konrad.zemek@…>, 7 years ago

Replying to Konrad Zemek <konrad.zemek@…>:

Basically, the future's destructor waits on lock that was already locked earlier in the callstack:

Just to avoid any miscommunication, I meant a mutex, not a lock. :)

comment:2 by viboes, 7 years ago

Please, could you try the develop branch in order to see if this is already fixed? I have done a lot of changes in it.

comment:3 by viboes, 7 years ago

Owner: changed from Anthony Williams to viboes
Status: newassigned

comment:4 by Konrad Zemek <konrad.zemek@…>, 7 years ago

The same deadlock happens in develop (e39703f).

I "solved" it for testing purposes by reordering variable initialization in do_continuation, but it's obviously the wrong way: if the future's destructor happens-before relocker's destructor, then relocker locks an already destroyed mutex:

diff --git a/include/boost/thread/future.hpp b/include/boost/thread/future.hpp
index e2dcb43..16b6270 100644
--- a/include/boost/thread/future.hpp
+++ b/include/boost/thread/future.hpp
@@ -230,9 +230,9 @@ namespace boost
             void do_continuation(boost::unique_lock<boost::mutex>& lock)
             {
                 if (! continuations.empty()) {
+                  relocker rlk(lock);
                   continuations_type the_continuations = continuations;
                   continuations.clear();
-                  relocker rlk(lock);
                   for (continuations_type::iterator it = the_continuations.begin(); it != the_continuations.end(); ++it) {
                     (*it)->launch_continuation();
                   }

Following is the stack trace from the application using Boost.Thread from develop:

#0  __lll_lock_wait () at ../nptl/sysdeps/unix/sysv/linux/x86_64/lowlevellock.S:135
#1  0x00007f9a9553856a in _L_lock_913 () from /lib/x86_64-linux-gnu/libpthread.so.0
#2  0x00007f9a95538390 in __GI___pthread_mutex_lock (mutex=0x7f9a8c000ed0) at ../nptl/pthread_mutex_lock.c:79
#3  0x00000000004bb872 in pthread_mutex_lock (m=0x7f9a8c000ed0) at /usr/include/boost/thread/pthread/mutex.hpp:62
#4  boost::mutex::lock (this=0x7f9a8c000ed0) at /usr/include/boost/thread/pthread/mutex.hpp:116
#5  0x00000000004c4b83 in boost::unique_lock<boost::mutex>::lock (this=0x7f9a93139d30)
    at /usr/include/boost/thread/lock_types.hpp:346
#6  0x00000000004c4ceb in boost::unique_lock<boost::mutex>::unique_lock (this=0x7f9a93139d30, m_=...)
    at /usr/include/boost/thread/lock_types.hpp:124
#7  0x00000000004be583 in boost::detail::shared_state_base::dec (this=0x7f9a8c000e90)
    at /usr/include/boost/thread/future.hpp:197
#8  0x00000000004ce1ae in boost::detail::basic_future<void>::~basic_future (this=0x1144a68, 
    __in_chrg=<optimized out>) at /usr/include/boost/thread/future.hpp:1203
#9  0x00000000004c602e in boost::future<void>::~future (this=0x1144a68, __in_chrg=<optimized out>)
    at /usr/include/boost/thread/future.hpp:1556
#10 0x00000000004de3c6 in boost::detail::future_unwrap_shared_state<boost::future<boost::future<void> >, void>::~future_unwrap_shared_state (this=0x1144950, __in_chrg=<optimized out>) at /usr/include/boost/thread/future.hpp:5065
#11 0x00000000004de414 in boost::detail::future_unwrap_shared_state<boost::future<boost::future<void> >, void>::~future_unwrap_shared_state (this=0x1144950, __in_chrg=<optimized out>) at /usr/include/boost/thread/future.hpp:5065
#12 0x00000000004de44c in boost::checked_delete<boost::detail::future_unwrap_shared_state<boost::future<boost::future<void> >, void> > (x=0x1144950) at /usr/include/boost/core/checked_delete.hpp:34
#13 0x00000000004e01e2 in boost::detail::sp_counted_impl_p<boost::detail::future_unwrap_shared_state<boost::future<boost::future<void> >, void> >::dispose (this=0x1144150) at /usr/include/boost/smart_ptr/detail/sp_counted_impl.hpp:78
#14 0x00000000004bab3c in boost::detail::sp_counted_base::release (this=0x1144150)
    at /usr/include/boost/smart_ptr/detail/sp_counted_base_gcc_x86.hpp:146
#15 0x00000000004babff in boost::detail::shared_count::~shared_count (this=0x7f9a8c000988, 
    __in_chrg=<optimized out>) at /usr/include/boost/smart_ptr/detail/shared_count.hpp:443
#16 0x00000000004becd6 in boost::shared_ptr<boost::detail::shared_state_base>::~shared_ptr (this=0x7f9a8c000980, 
    __in_chrg=<optimized out>) at /usr/include/boost/smart_ptr/shared_ptr.hpp:323
#17 0x00000000004d98fa in std::_Destroy<boost::shared_ptr<boost::detail::shared_state_base> > (
    __pointer=0x7f9a8c000980) at /usr/include/c++/4.9/bits/stl_construct.h:93
#18 0x00000000004d5d29 in std::_Destroy_aux<false>::__destroy<boost::shared_ptr<boost::detail::shared_state_base>*>
    (__first=0x7f9a8c000980, __last=0x7f9a8c000990) at /usr/include/c++/4.9/bits/stl_construct.h:103
#19 0x00000000004d070d in std::_Destroy<boost::shared_ptr<boost::detail::shared_state_base>*> (
    __first=0x7f9a8c000980, __last=0x7f9a8c000990) at /usr/include/c++/4.9/bits/stl_construct.h:126
#20 0x00000000004c8587 in std::_Destroy<boost::shared_ptr<boost::detail::shared_state_base>*, boost::shared_ptr<boost::detail::shared_state_base> > (__first=0x7f9a8c000980, __last=0x7f9a8c000990)
    at /usr/include/c++/4.9/bits/stl_construct.h:151
#21 0x00000000004c255f in std::vector<boost::shared_ptr<boost::detail::shared_state_base>, std::allocator<boost::shared_ptr<boost::detail::shared_state_base> > >::~vector (this=0x7f9a93139f80, __in_chrg=<optimized out>)
    at /usr/include/c++/4.9/bits/stl_vector.h:424
#22 0x00000000004be6f0 in boost::detail::shared_state_base::do_continuation (this=0x7f9a8c000e90, lock=...)
    at /usr/include/boost/thread/future.hpp:238
#23 0x00000000004be860 in boost::detail::shared_state_base::mark_finished_internal (this=0x7f9a8c000e90, lock=...)
    at /usr/include/boost/thread/future.hpp:264
#24 0x00000000004beea5 in boost::detail::shared_state<void>::mark_finished_with_result_internal (
    this=0x7f9a8c000e90, lock=...) at /usr/include/boost/thread/future.hpp:716
#25 0x00000000004e0761 in boost::detail::future_unwrap_shared_state<boost::future<boost::future<void> >, void>::launch_continuation (this=0x7f9a8c000e90) at /usr/include/boost/thread/future.hpp:5096
#26 0x00000000004be6a5 in boost::detail::shared_state_base::do_continuation (this=0x7f9a8c0012e0, lock=...)
    at /usr/include/boost/thread/future.hpp:237
#27 0x00000000004be860 in boost::detail::shared_state_base::mark_finished_internal (this=0x7f9a8c0012e0, lock=...)
    at /usr/include/boost/thread/future.hpp:264
#28 0x00000000004beea5 in boost::detail::shared_state<void>::mark_finished_with_result_internal (
    this=0x7f9a8c0012e0, lock=...) at /usr/include/boost/thread/future.hpp:716
#29 0x00000000004e0761 in boost::detail::future_unwrap_shared_state<boost::future<boost::future<void> >, void>::launch_continuation (this=0x7f9a8c0012e0) at /usr/include/boost/thread/future.hpp:5096
#30 0x00000000004be6a5 in boost::detail::shared_state_base::do_continuation (this=0x7f9a8c000a20, lock=...)
    at /usr/include/boost/thread/future.hpp:237
#31 0x00000000004be785 in boost::detail::shared_state_base::set_continuation_ptr (this=0x7f9a8c000a20, 
    continuation=..., lock=...) at /usr/include/boost/thread/future.hpp:251
#32 0x00000000004e0675 in boost::detail::future_unwrap_shared_state<boost::future<boost::future<void> >, void>::launch_continuation (this=0x7f9a8c0012e0) at /usr/include/boost/thread/future.hpp:5087
#33 0x00000000004be6a5 in boost::detail::shared_state_base::do_continuation (this=0x7f9a8c0010d0, lock=...)
    at /usr/include/boost/thread/future.hpp:237
#34 0x00000000004be860 in boost::detail::shared_state_base::mark_finished_internal (this=0x7f9a8c0010d0, lock=...)
    at /usr/include/boost/thread/future.hpp:264
#35 0x00000000004e83ef in boost::detail::shared_state<boost::future<void> >::mark_finished_with_result_internal(boost::future<void>&&, boost::unique_lock<boost::mutex>&) (this=0x7f9a8c0010d0, 
    result_=<unknown type in /home/konrad/plgrid/helpers/debug/test/unit/retrier_test, CU 0xa555, DIE 0x37494>, 
    lock=...) at /usr/include/boost/thread/future.hpp:525
#36 0x00000000004e8361 in boost::detail::shared_state<boost::future<void> >::mark_finished_with_result(boost::future<void>&&) (this=0x7f9a8c0010d0, 
    result_=<unknown type in /home/konrad/plgrid/helpers/debug/test/unit/retrier_test, CU 0xa555, DIE 0x37494>)
    at /usr/include/boost/thread/future.hpp:553
#37 0x00000000004e8280 in _ZN5boost6detail41future_executor_continuation_shared_stateINS_9executors17basic_thread_poolENS_6futureIvEES5_ZN3one13communication6layers7RetrierI10LowerLayerE4sendESsiEUlT_E_E3runENS_10shared_ptrINS0_17shared_state_baseEEE (that_=...) at /usr/include/boost/thread/future.hpp:4284
#38 0x00000000004e80fa in _ZN5boost6detail6run_itINS0_41future_executor_continuation_shared_stateINS_9executors17basic_thread_poolENS_6futureIvEES6_ZN3one13communication6layers7RetrierI10LowerLayerE4sendESsiEUlT_E_EEEclEv (
    this=0x7f9a8c001268) at /usr/include/boost/thread/future.hpp:4256
#39 0x00000000004e7f7c in _ZN5boost6detail16nullary_functionIFvvEE9impl_typeINS0_6run_itINS0_41future_executor_continuation_shared_stateINS_9executors17basic_thread_poolENS_6futureIvEESA_ZN3one13communication6layers7RetrierI10LowerLayerE4sendESsiEUlT_E_EEEEE4callEv (this=0x7f9a8c001260) at /usr/include/boost/thread/detail/nullary_function.hpp:52
#40 0x00000000004bf6af in boost::detail::nullary_function<void ()>::operator()() (this=0x7f9a9313a690)
    at /usr/include/boost/thread/detail/nullary_function.hpp:125
#41 0x00000000004bf70d in boost::executors::basic_thread_pool::worker_thread (this=0x1145ac0)
    at /usr/include/boost/thread/executors/basic_thread_pool.hpp:91
#42 0x00000000004e53d7 in boost::detail::invoke<void (boost::executors::basic_thread_pool::*)(), boost::executors::basic_thread_pool<>*>(void (boost::executors::basic_thread_pool::*&&)(), boost::executors::basic_thread_pool<>*&&, (boost::executors::basic_thread_pool<>*&&)...) (
    f=<unknown type in /home/konrad/plgrid/helpers/debug/test/unit/retrier_test, CU 0xa555, DIE 0x75e98>, 
    a0=<unknown type in /home/konrad/plgrid/helpers/debug/test/unit/retrier_test, CU 0xa555, DIE 0x75e9d>)
    at /usr/include/boost/thread/detail/invoke.hpp:77
#43 0x00000000004e3687 in boost::detail::thread_data<void (boost::executors::basic_thread_pool::*)(), boost::executors::basic_thread_pool*>::run2<1ul> (this=0x1145ca0) at /usr/include/boost/thread/detail/thread.hpp:75
#44 0x00000000004e0ad0 in boost::detail::thread_data<void (boost::executors::basic_thread_pool::*)(), boost::executors::basic_thread_pool*>::run (this=0x1145ca0) at /usr/include/boost/thread/detail/thread.hpp:81
#45 0x00007f9a9575cd8a in ?? () from /usr/lib/x86_64-linux-gnu/libboost_thread.so.1.58.0
#46 0x00007f9a955360a5 in start_thread (arg=0x7f9a9313d700) at pthread_create.c:309
#47 0x00007f9a94d3dcfd in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:111

in reply to:  4 comment:5 by viboes, 7 years ago

Replying to Konrad Zemek <konrad.zemek@…>:

The same deadlock happens in develop (e39703f).

I "solved" it for testing purposes by reordering variable initialization in do_continuation, but it's obviously the wrong way: if the future's destructor happens-before relocker's destructor, then relocker locks an already destroyed mutex:

I need to check if this situation is possible. Thanks for signaling it.

comment:6 by viboes, 7 years ago

The code in develop (or >=boost.1.58) contains now

#if defined BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
            void do_continuation(boost::unique_lock<boost::mutex>& lock)
            {
                if (! continuations.empty()) {
                  continuations_type the_continuations = continuations;
                  continuations.clear();
                  relocker rlk(lock);
                  for (continuations_type::iterator it = the_continuations.begin(); it != the_continuations.end(); ++it) {
                    (*it)->launch_continuation();
                  }
                }
            }
#else
            void do_continuation(boost::unique_lock<boost::mutex>&)
            {
            }
#endif

Please could you give a try?

in reply to:  6 comment:7 by viboes, 7 years ago

Replying to viboes:

The code in develop (or >=boost.1.58) contains now

#if defined BOOST_THREAD_PROVIDES_FUTURE_CONTINUATION
            void do_continuation(boost::unique_lock<boost::mutex>& lock)
            {
                if (! continuations.empty()) {
                  continuations_type the_continuations = continuations;
                  continuations.clear();
                  relocker rlk(lock);
                  for (continuations_type::iterator it = the_continuations.begin(); it != the_continuations.end(); ++it) {
                    (*it)->launch_continuation();
                  }
                }
            }
#else
            void do_continuation(boost::unique_lock<boost::mutex>&)
            {
            }
#endif

Please could you give a try?

Forget this message :(

comment:8 by viboes, 7 years ago

Hi,

we have fixed some issues with in future.hpp (https://github.com/boostorg/thread/commit/60a8cb9b5c69423ee0bea403cacc971606575f01).

Please, could you check with the develop branch?

comment:9 by viboes, 7 years ago

Type: BugsSupport Requests

Moved to support until we have some news.

comment:10 by viboes, 6 years ago

Milestone: To Be Determined
Resolution: worksforme
Status: assignedclosed

I believe this issue has already been fixed.

Please reopen it if it is not the case.

Note: See TracTickets for help on using tickets.