必须用户提供的terminate()函数是否是线程安全的?

Pio*_*ycz 11 c++ multithreading terminate-handler c++11

http://en.cppreference.com/w/cpp/error/terminate中所述,有很多理由要求终止.我可以想象几乎在同一时间的情况,其中一些原因发生在两个线程中.

Q1终止功能设置std::set_terminate可以同时被调用两次或更多次,同时我的意思是第一次呼叫在第一次结束之前开始.

  Thread1   Thread2
    |          |
    _          |
    t          |
    e          |
    r          |
    m          |
    i          _
    n          t
    a          e
    t          r
    e          m
    -          ?
Run Code Online (Sandbox Code Playgroud)

Q2如果Q1 == YES,那么如果第一次终止结束会发生什么.我想如果它以std :: abort结束,那么程序结束,但是如果用户提供的终止不会中止程序会发生什么?

Q3是否在std::set_terminate导致此终止调用的线程的上下文中调用了terminate函数?

How*_*ant 7

Q1

是的,std::terminate可以同时调用.

Q2

该标准表示,如果terminate_handler不"在不返回调用者的情况下终止程序的执行",则它是未定义的行为.在我熟悉的实现中,如果terminate_handler通常或异常地返回的尝试abort()将被调用.

Q3

设置的函数std::terminate是全局的,而不是本地的线程.所以一个线程可以影响另一个.

在C++ 98/03中,由于未捕获异常而调用的terminate_handlerused terminate是在抛出异常时生效的,而不是terminate实际调用时生效的异常(尽管它们通常是相同的).

在C++ 11中,这已经改变,标准现在说使用的处理程序是当时terminate调用的处理程序.这种改变是错误的,很可能在未来的草案中得到纠正.以下是跟踪此问题的LWG问题:

http://cplusplus.github.com/LWG/lwg-active.html#2111

更新

在KS的Lenexa举行的2015年春季会议上,LWG决定对现有行为进行标准化,terminate_handler如果set_terminate在堆栈展开期间调用新的行为,则将其指定为未指定.即允许实现遵循C++ 98/03规则或C++ 11规则.

为了使你的代码可移植,如果你需要设置a terminate_handler,在程序启动期间,在抛出任何异常之前这样做,并且不要养成在此set_terminate之后调用的习惯.