R..*_*R.. 10 c linux posix signals pthreads
在POSIX线程的大多数实现中,在新创建的线程处于能够运行应用程序代码的一致状态之前,需要进行一些初始化.这可能涉及解锁线程结构中的锁,在使用一个的实现中初始化"线程寄存器",初始化线程本地数据(编译器级别的TLS或POSIX线程特定的数据)等.我找不到清楚的保证在线程可以接收任何信号之前完成所有这些初始化; 我能找到的最接近的是2.4.3:
下表定义了一组异步信号安全的函数.因此,应用程序可以无限制地调用信号捕获功能:
...
据推测,这些函数中的一些(至少fork
必须检查由pthread_atfork
函数建立的全局状态)取决于线程处于一致的初始化状态.
困扰我的一件事是我已经阅读了很多glibc/nptl源代码,并且找不到任何显式同步来防止新创建的线程在完全初始化之前处理信号.我希望线程调用pthread_create
在调用之前阻塞所有信号clone
,并且一旦初始化完成,新线程就会解除阻塞它们,但是我找不到任何代码,也没有在strace
输出中看到它.
(我不认为这是一个真正的答案,但对于评论来说太大了)
这是一个非常有趣的问题。我查看了 glibc 代码以pthread_create
了解它的行为方式,除非我完全遗漏了一些东西,否则似乎没有任何特殊行为可以阻止这种情况(例如阻止之前的所有信号clone
并在之后的子级中取消阻止它们)一些设置(记录线程创建时间并设置 C++ 捕获所有异常处理程序之后,即使在 C 代码中也会发生})。
我期待找到一条评论提到这种情况的可能性,甚至可能提到 POSIX 说要做什么(或者提到它没有说要做什么)。
也许您应该始终使用pthread_create
代码来阻止和恢复信号,并通过取消阻止调用来启动所有线程函数。
这很可能是 pthreads(或 glibc 或我对代码的理解)中的一个过度站点。