将异常抛出到另一个线程

时间:2016-04-07 18:16:12

标签: multithreading c++11 exception posix

这不涉及任何涉及捕获一个线程中从另一个线程抛出的异常的问题。

我有一个产生线程的代码,它会自动完成。

在将来的某个时刻,我希望能够在另一个帖子中抛出两个例外中的一个(即terminateinterrupt)。

执行此操作的一种方法是让变量共享并让另一个线程定期检查是否应该将其杀死。我的偏好是没有它检查的约束(一些代码将独立于执行线程的库,并且已经写入以进行检查)。

在我理想的解决方案中,您最终可能会遇到这样的情况:调试时,您可能会发现auto i = 1 + 1引发异常,因为另一个线程告诉您的线程抛出,而您只是< em>发生当时正在开启。

我有办法做到这一点吗?

2 个答案:

答案 0 :(得分:1)

是的,有可能在另一个线程中引发异常。

我将假设您知道在正常程序中不应执行此操作的所有充分原因。但是,例如,作为测试套件,调试工具或其他与python内部相关的程序的一部分,这可能会有所帮助。

大约从https://gist.github.com/liuw/2407154

解除
import ctypes

def ctype_async_raise(target_tid, exception):
    ret = ctypes.pythonapi.PyThreadState_SetAsyncExc(ctypes.c_long(target_tid), ctypes.py_object(exception))
    # ref: http://docs.python.org/c-api/init.html#PyThreadState_SetAsyncExc
    if ret == 0:
        raise ValueError("Invalid thread ID")
    elif ret > 1:
        # Huh? Why would we notify more than one threads?
        # Because we punch a hole into C level interpreter.
        # So it is better to clean up the mess.
        ctypes.pythonapi.PyThreadState_SetAsyncExc(target_tid, NULL)
        raise SystemError("PyThreadState_SetAsyncExc failed")

答案 1 :(得分:0)

我认为线程A中的异常在线程B中没有概念意义,因为异常的核心概念是堆栈的展开,而线程A的堆栈与线程B的堆栈不同。

你可以做的是在线程A中抛出异常,在线程A中有一个异常处理程序捕获异常并通过某种方式通过线程B通知相关细节来处理它,并且当线程B收到通知时可以通过抛出来响应它自己的异常类似于最初在线程A中抛出的异常。

至于如何实现通知和数据传输,您可以使用任何常用的跨线程通知/通信机制(共享原子变量和轮询,套接字,管道,互斥锁定的FIFO消息队列等)。 / p>

  

在我理想的解决方案中,您最终可能会遇到调试,   您可能会发现auto i = 1 + 1会因为另一个而引发异常   线程告诉你的线程抛出,这就是你刚刚发生的那条线   当时要开始。

我认为这被称为异步异常,我不认为标准C ++支持它。微软有structured exception handling(SEH)那样做,但这是一个专有/非标准功能。