【问题标题】:Are all threads halted when one of them receives a signal and none of them block it?当其中一个线程接收到信号并且没有一个线程阻塞它时,是否所有线程都停止了?
【发布时间】:2015-09-28 14:44:12
【问题描述】:

我正在 Linux 上运行一个用 C 语言编写的多线程应用程序。

要停止执行,我发送SIGINT 并从信号处理程序调用一些清理例程,最后调用exit(0)

当处理程序执行清理例程时,其他线程是否仍在运行或可能运行(上下文切换)?

【问题讨论】:

  • 您不想在信号处理程序中调用exit(),因为它不受异步信号安全的保证。请致电_exit()。或者更好的是根本不从信号处理程序结束程序,而是通过让所有线程正常结束来执行优雅关闭。供参考:man7.org/linux/man-pages/man7/signal.7.html

标签: c linux multithreading pthreads signals


【解决方案1】:

处理信号不会导致在信号处理程序执行期间暂停其他线程。此外,从信号处理程序调用清理所需的大多数函数(甚至包括exit!)通常是不安全的,除非您可以确保它不会中断异步信号不安全函数。

您应该做的只是存储SIGINT 以某种异步信号安全的方式接收的事实,并让程序在该条件下作为其正常执行流程的一部分在信号处理程序之外进行操作。然后,您可以与其他线程正确同步(使用互斥锁、条件变量等)以实现正确、安全的关闭。理想的方法是甚至不安装信号处理程序,而是阻止所有信号并有一个专用的信号处理线程在循环中调用sigwaitinfo 以接受信号。

【讨论】:

    【解决方案2】:

    是的,信号被传递到一个线程,以未指定的方式选择。但是,只考虑不阻塞信号的线程;如果所有线程都阻塞了信号,它会一直排队,直到有一个线程解除阻塞。

    (因此,如果您让 所有 个线程阻塞信号,您可以将信号用作确定性的进程间同步机制,例如使用 sigwait。)

    【讨论】:

    • 但是如果他们不阻塞信号,其他人可以运行,而接收信号的人正在处理它吗?因为我有一个日志,并且在信号处理程序打印“Exit”之后,我有不同线程引起的打印。
    • 是的,不接收信号的线程不会做任何特别的事情。他们不知道另一个线程收到了信号。
    • @R.. 发布另一个答案 :-)
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-29
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多