我已经读到,如果主程序的线程在调用信号处理程序之前已锁定了Mutex,则在信号处理程序中使用MUTEX会造成死锁。 我还阅读了建议信号处理程序应该使用std :: iS_lock_free()返回true的原子类型的建议。 std :: atomic_flag就是一种类型,cppReference甚至在其STD:: atomic_flagpage.
中甚至具有Spinlock实现。,我的问题是:如果我用自旋锁来保护临界部分,而不是信号处理程序中的静音,那么在主要程序中,僵局仍然不可能吗? 如果主程序中的线程锁定了自旋锁,然后信号处理程序运行并试图锁定Spinlock,不会发生僵局?
如果我用自旋锁来保护临界部分,而不是信号处理程序中的静音lock,则在主要程序中仍然是可能的吗?原子学的建议也只是一个笨拙。专门为信号设计的类型是是的,您的评估是正确的。线程仍然可以僵局本身。更具体地说,如果该线程无法运行,您迫不及待地等待线程解锁二线(或类似)。您可以检测到一个互惠件是锁定的,然后放弃,但您迫不及待。但是,即使那是带有常规静音的外部规格,因为它们不在
ASYNC-SIGNAL-SAFE函数的列表中。
volatile sig_atomic_t
,但您只能加载并存储它。原子化原子需要完成原子。这是因为在读取和编写变量的读取工程操作之间可能会出现信号。加载和存储可能需要多个指令的较大对象也是如此。但是有一些例外:
一些信号之类的信号仅在某些系统呼叫中发生,因此没有任何风险中断其他代码 您可以暂时阻止信号以更新共享状态,但通常更昂贵
处理复杂案例的正确方法是将工作推迟到其他线程或回到主线程。一个常见的模式是制作SIGPIPE
pipe
。然后将信号处理程序的简短消息写给文件描述符。然后可以从另一个文件描述符拾取消息并对其进行处理。这在GUI应用中特别有效,因为GUI事件循环可以将这些消息与其他所有内容一起处理。在理论中,您可以使用此模式等待接收线的响应,但是却不要这样做。该线程可能仍会被阻塞,等待正在运行信号处理程序的螺纹固定的静音。另一个僵局
socketpair