POSIX线程和信号 [英] POSIX threads and signals

查看:121
本文介绍了POSIX线程和信号的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我一直在试图了解如何POSIX线程和POSIX信号相互作用的复杂性。特别是我感兴趣的:


  • 什么来控制线程的信号被传递到的最佳方式(假定它不是在首位是致命的)?

  • 什么是告诉另一个线程(实际上可能是忙),该信号已经到来的最好方法? (我已经知道这是一个坏主意,用从信号处理程序的pthread条件变量是。)

  • 如何安全地处理传递一个信号发生了其他线程的信息?这是否需要在信号处理程序会发生什么? (我做的不是一般的想杀死其他线程。我需要一个远微妙的方法)

有关为什么我要这样的参考,我研究如何将 TclX 包来支持线程​​转换,或拆分它,至少做一些有用的部分支持线程。信号是特别感兴趣的那些部分中的一个。


解决方案

  

      
  • 什么是控制哪个线程的最佳途径
      信号被输送到<?/ LI>
      

作为@ zoli2k指出,明确提名单个线程来处理您要处理的所有信号(或一组各具特定的信号职责线程),是一个很好的技术。


  

      
  • 什么是告诉另一个线程(实际上可能是忙)的最佳方法
      该信号已经来临?[...]

  •   
  • 如何安全地处理传递信息的信号已经出现
      给其他线程?这是否需要在信号处理程序发生?

  •   

我不会说最好,但这里是我的建议:

所有需要的信号主要,让所有线程都继承的信号掩码。于是,时尚的特殊信号接收线程作为一个信号驱动的事件循环,调度初来乍到的信号为其他线程内通信

要做到这一点最简单的方法是在使用线程接收信号在一个循环<一个href=\"http://pubs.opengroup.org/onlinepubs/9699919799/functions/sigtimedwait.html\"><$c$c>sigwaitinfo sigtimedwait 。然后该线程将信号转换不知何故,也许广播 pthread_cond_t的,以唤醒其他线程更多的I / O,在一个特定应用的线程安全的队列入队的命令,不管

另外,特殊螺纹可以让信号传递到信号处理程序,揭露交付只有当准备处理的信号。 (经处理的信号传递往往比通过调用sigwait 系列信号接收更容易出错,但是。)在这种情况下,接收器的信号处理程序执行一些简单而async-信号安全操作:设置 sig_atomic_t 旗帜,号召 sigaddset(安培; signals_i_have_seen_recently,latest_sig)()一个字节非阻塞自管等。然后,在其背部屏蔽主循环中,线程通信接收信号到其它线程如上

更新时间: @caf正确地指出,调用sigwait 办法优越。)

I've been trying to understand the intricacies of how POSIX threads and POSIX signals interact. In particular, I'm interested in:

  • What's the best way to control which thread a signal is delivered to (assuming it isn't fatal in the first place)?
  • What is the best way to tell another thread (that might actually be busy) that the signal has arrived? (I already know that it's a bad idea to be using pthread condition variables from a signal handler.)
  • How can I safely handle passing the information that a signal has occurred to other threads? Does this need to happen in the signal handler? (I do not in general want to kill the other threads; I need a far subtler approach.)

For reference about why I want this, I'm researching how to convert the TclX package to support threads, or to split it up and at least make some useful parts support threads. Signals are one of those parts that is of particular interest.

解决方案

  • What's the best way to control which thread a signal is delivered to?

As @zoli2k indicated, explicitly nominating a single thread to handle all signals you want handled (or a set of threads each with specific signal responsibilities), is a good technique.

  • What is the best way to tell another thread (that might actually be busy) that the signal has arrived?[...]
  • How can I safely handle passing the information that a signal has occurred to other threads? Does this need to happen in the signal handler?

I won't say "best," but here's my recommendation:

Block all desired signals in main, so that all threads are inherit that signal mask. Then, fashion the special signal receiving thread as a signal-driven event loop, dispatching newly arrived signals as some other intra-thread communication.

The simplest way to do this is to have the thread accept signals in a loop using sigwaitinfo or sigtimedwait. The thread then converts the signals somehow, perhaps broadcasting a pthread_cond_t, waking up other threads with more I/O, enqueuing a command in an application-specific thread-safe queue, whatever.

Alternatively, the special thread could allow signals to be delivered to a signal handler, unmasking for delivery only when ready to handle signals. (Signal delivery via handlers tends to be more error-prone than signal acceptance via the sigwait family, however.) In this case, the receiver's signal handler performs some simple and async-signal-safe action: setting sig_atomic_t flags, calling sigaddset(&signals_i_have_seen_recently, latest_sig), write() a byte to a non-blocking self-pipe, etc. Then, back in its masked main loop, the thread communicates receipt of the signal to other threads as above.

(UPDATED @caf rightly points out that sigwait approaches are superior.)

这篇关于POSIX线程和信号的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆