Boost logo

Boost :

Subject: Re: [boost] [thread] thread_proxy's catch(...) destroys my stack info for unhandled exceptions
From: Dmitry Goncharov (dgoncharov_at_[hidden])
Date: 2008-12-27 07:07:19


Your f1() and f2() are callback function. If such a callback function
throws an exception the program should be terminated, since the os
cannot handle the exception for you.
That's reasonable to embrace callbacks like f1() with a catch all block
and deal with the exception the way you want.
E.g.
void f1()
{
    try { throw 1; }
    catch(...) {abort();} // Here is your core dump.
}

If everybody did that there would be no need for boost::thread to
provide the catch all block.

BR, Dmitry

Roberto Gimenez wrote:
> When some unhandled exception is thrown inside my function, it would be good
> that is isn't actually handled, so I could collect the stack info from the
> core-dump. For example:
>
> #include <boost/thread.hpp>
>
> using namespace std;
> using namespace boost;
>
> void f1() { throw 1; }
> void f2() { throw 1; }
> void f() { f1(); f2(); }
>
> int main(int argc, char** argv)
> {
>
> thread t(f);
> t.join();
>
> return (EXIT_SUCCESS);
> }
>
>
> Whe run it, the core-dump's stack info is:
>
> ----------------- lwp# 1 / thread# 1 --------------------
> ffffffff7ecd2f20 __lwp_park (100108658, 100108640, ...
> ffffffff7eccc748 cond_wait_queue (100108658, 100108640, ...
> ffffffff7ecccca8 cond_wait (100108658, 100108640, ...
> ffffffff7ecccce4 pthread_cond_wait (100108658, 100108640,...
> ffffffff7f809ff4 void boost::thread::join() (ffffffff7ffff518, ...
> 0000000100004168 main (1, ffffffff7ffff608, ffffffff7ffff618, ...
> 0000000100003a7c _start (0, 0, 0, 0, 0, 0) + 17c
> ----------------- lwp# 2 / thread# 2 --------------------
> ffffffff7ecd40a4 _lwp_kill (6, 0, ffffffff7edf7338, ...
> ffffffff7ec4a68c abort (1, 1b8, ffffffff7f106f10, ...
> ffffffff7f106a04 void __Cimpl::default_terminate() (0, 0, ...
> ffffffff7f809770 thread_proxy (100108610, 1001086dd, 2c, ...
> ffffffff7ecd2e7c _lwp_start (0, 0, 0, 0, 0, 0)
>
> With this information I cannot know where the exception was thrown.
>
>
> So I commented the catch(...) part in libs/thread/src/pthread/thread.cpp:
>
> extern "C"
> {
> void* thread_proxy(void* param)
> {
> boost::detail::thread_data_ptr thread_info =
> static_cast<boost::detail::thread_data_base*>(param)->self;
> thread_info->self.reset();
> detail::set_current_thread_data(thread_info.get());
> try
> {
> thread_info->run();
> }
> catch(thread_interrupted const&)
> {
> }
> //catch(...)
> //{
> // std::terminate();
> //}
>
> detail::tls_destructor(thread_info.get());
> detail::set_current_thread_data(0);
> boost::lock_guard<boost::mutex> lock(thread_info->data_mutex);
> thread_info->done=true;
> thread_info->done_condition.notify_all();
> return 0;
> }
> }
>
> And recompiled boost, now the core dump's stack info is the desired one:
>
> ----------------- lwp# 1 / thread# 1 --------------------
> ffffffff7ecd2f20 __lwp_park (100108658, 100108640, 0, 4, 11fb1c, ...
> ffffffff7eccc748 cond_wait_queue (100108658, 100108640, 0, 0, ...
> ffffffff7ecccca8 cond_wait (100108658, 100108640, ffffffff7ed00358,...
> ffffffff7ecccce4 pthread_cond_wait (100108658, 100108640, ...
> ffffffff7f809f54 void boost::thread::join() (ffffffff7ffff518, ...
> 0000000100004168 main (1, ffffffff7ffff608, ffffffff7ffff618, ...
> 0000000100003a7c _start (0, 0, 0, 0, 0, 0) + 17c
> ----------------- lwp# 2 / thread# 2 --------------------
> ffffffff7ecd40a4 _lwp_kill (6, 0, ffffffff7edf7338, ...
> ffffffff7ec4a68c abort (1, 1b8, ffffffff7f106f10, ...
> ffffffff7f106a04 void __Cimpl::default_terminate() (ffffffff7f214718, ...
> ffffffff7f1067f4 void __Cimpl::ex_terminate() (ffffffff7f2106c0, 0, 0, ...
> ffffffff7f1074c8 _ex_throw_body (ffffffff7f2106c0, 0, ffffffff7e2fbf50, ...
> ffffffff7f10740c void __Crun::ex_throw(void*,...
> 0000000100004064 void f1() (0, 0, ffffffff7edf7f80, ...
> 00000001000040fc void f() (ffffffff7f915528, 100108610, ...
> 00000001000053c0 void boost::detail::thread_data<void(*)()>::run() (...
> ffffffff7f8095b4 thread_proxy (100108610, 3, 100106bd8, 100108610...
> ffffffff7ecd2e7c _lwp_start (0, 0, 0, 0, 0, 0)
>
>
> I can know now where the unexpected/unhandled exception was thrown.
> I could solve my problem partially, puting throw() exception specs
> everywhere, so when some unexpected exception is thrown, the throw()
> will stop it. Unfortunatelly, it whould stop at the calling function,
> and the stack will tell me that some unexpected exception was thrown
> by any of the functions inside the caller. This is worse than having
> a stack info like the above one because in this case I wouldn't know
> who raised the unexpected exception. In the above stack info I can know
> who did it.
>
> So why is:
>
> catch(...)
> {
> std::terminate();
> }
>
> there? It looks unnecesary.
>
> _______________________________________________
> Unsubscribe & other changes: http://lists.boost.org/mailman/listinfo.cgi/boost
>


Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk