在Linux内核中,spin_lock_irqsave()是否保护我免受信号处理程序,页面错误,调度schedule()的影响?

时间:2016-06-29 13:15:35

标签: c linux multithreading linux-kernel locks

我对Linux内核中的中断构成了一点困惑。根据我的理解,spin_lock_irqsave()/ spin_lock_irqrestore()确保我的关键部分不会被中断处理程序抢占。很公平。

但我对中断处理程序的构成有点困惑。首先,我并非100%确定我也能够免受softirq的抢先。是这种情况吗?

例外情况怎么样?据我所知,他们和中断一样,但不是真的。当我使用spin_lock_irqsave()时,我是否受到页面错误处理程序的抢占保护?发生页面错误时究竟发生了什么,用于处理它们的机制与中断完全相同?

信号处理程序怎么样?我不明白这些是如何实施的。如果我发送信号SIGTERM,SIGINT或SIGKILL信号该怎么办?这是用软IRQ实现的吗?别的什么?当我使用spin_lock_irqsave()时,这样的信号可以抢占我的关键部分吗?或者完全没有,因为这些信号只在用户空间处理?

如何调用schedule()?当我使用spin_lock_irqsave()时,即使在我的关键部分,那些人是否可以随时抢占我?

我想我真正想知道的是当我使用spin_lock_irqsave()时,究竟可以取代什么。没有人使用与我相同的锁,也没有使用中断处理程序。那些其他的东西怎么样?那么softirqs / tasklets / work队列呢?

最后,spin_lock_irqsave()比spin_lock_bh()强吗?即,spin_lock_irqsave()是否阻止从下半部分抢占(即softirqs,tasklet和工作队列)?

我一直在谷歌搜索所有这些,但我发现很难找到明确的答案。

1 个答案:

答案 0 :(得分:4)

spin_lock_irqsave锁定并禁用(暂时屏蔽)中断。在释放锁定之前不会遇到中断(否则重新启用中断 - 您不应该这样做)。同样,你不会也不能被抢占,因为抢占需要中断才能导致控制权转移。

中断是来自外部设备的信号,表示需要注意。 CPU硬件支持一种机制,允许自动将控制转移到一个"中断处理程序"当中断信号被置位时(但这可以暂时屏蔽,这是spin_lock_irqsave所做的)。

异常类似于中断,除非它们是由程序执行而非外部硬件/设备引起的。所以这包括被零除,非法指令,页面错误。除了最不寻常的情况之外,您的代码应该确保没有例外。例如,当您持有旋转锁时,不应该导致页面错误。这将导致内核OOPS。

信号处理程序主要是用户模式概念。发送给进程的信号在适当时由内核明确检查,并且直接导致操作(如进程终止)或导致下一步返回到该进程中的用户模式用户代码信号处理程序。在持有自旋锁时,您不应该访问任何可以执行此操作的代码。

同样,您在持有旋转锁定时可能不会调用schedule,因为......

旋转锁旨在保持非常短的时间,以防止同时访问跨多个处理器共享的数据结构。中断被禁用的原因是你可以确保持有自旋锁的任务不会被抢占 - 因为如果有的话,其他的CPU可能是离开很长一段时间甚至是永远。

...而schedule专门用于让您放弃对其他任务的控制。

另见本文。具体细节可能已经过时,但所有概念仍然有效。 https://www.kernel.org/pub/linux/kernel/people/rusty/kernel-locking/