spin_lock_irqsave关中断后,为什么要再禁止抢占呢,不多余吗?

spin_lock_irqsave关中断后,为什么要再禁止抢占呢,不多余吗?

static inline unsigned long __raw_spin_lock_irqsave(raw_spinlock_t *lock)
{
        unsigned long flags;


        local_irq_save(flags);
        preempt_disable();
        spin_acquire(&lock->dep_map, 0, 0, _RET_IP_);
。。。



如果不禁止内核抢断,可能会有以下的情况发生(假设进程B比进程A具有更高的优先级):
进程A获得spinlock lock
进程B运行(抢占进程A)
进程B获取spinlock lock
由于进程B比进程A优先级高,所以进程B在进程A之前运行,而进程B需要进程A释放lock之后才能运行,于是,死锁



关中断跟禁止抢占之间没有关系么?
关掉中断之后,时钟肯定也关了,也就调度相关的代码就不会执行

我们知道,linux的进程调度时机有:
1、进程状态转换的时刻:进程终止、进程睡眠
2、当前的进程的时间片用完(current->counter=0)
3、设备驱动程序主动调用schedule
4、进程从中断、异常及系统调用返回用户态

这儿1、3不可能吧。2、4依赖时钟中断,我们关了本地中断(SP),那不就意味着不能抢占么?


转:

所以,你最开始的疑问:“关中断只是屏蔽了中断,并没有阻止任务切换,高优先级的任务任然可以抢占CPU并访问临界区和共享变量啊”

关了中断,就禁止了抢占,如果当前任务也没有进行主动调度,当然系统中也就不会出现比当前优先级更高的任务进入就绪了,也就谈不上去“抢占CPU并访问临界区和共享变量”了。(作者这里说加了条件“如果当前任务也没有进行主动调度”,那如果当前任务进行了主动调度会怎么样?我认为,若是在临界区中进行了主动调度,那么后果就是提问的人说的:“关中断只是屏蔽了中断,并没有阻止任务切换,高优先级的任务任然可以抢占CPU并访问临界区和共享变量”。by imjacob)
由以下网址为证:http://www.gdjy.com.cn/xuexi/UNIX-XIUGAI/ch02/os0203.htm 中2.3.4为证。
上面是这么说的:

关 中 断 之 后, 任 何 外 部 事 件 都 不 能 打 扰 处 理 机 连 续 执 行 临 界 区 程 序。 如 果 临 界 区 程 序 本 身 并 不 包 含 使 它 的 进 程 转 变 为 封 锁 状 态 的 因 素, 那 么 这 种 方 法 就 能 保 证 临 界 区 作 为 一 个 整 体 执 行。 这 种 方 法 的 优 点 是 简 单、 可 靠, 但 是 它 也 有 一 定 的 局 限 性 和 若 干 不 足 之 处。

(1) 它 不 能 用 于 多 处 理 机 系 统。 其 原 因 是: 由 于 该 系 统 中 的 多 个 处 理 机 都 有 其 各 自 的 中 断 开 关, 因 此 一 个 处 理 机 并 不 能 阻 止 在 其 它 处 理 机 上 运 行 的 进 程 进 入 同 类 临 界 区。

(2) 在 临 界 区 中 如 果 包 含 有 使 执 行 它 的 进 程 有 可 能 进 入 封 锁 状 态 的 因 素, 则 也 不 能 使 用 这 种 方 法。 因 为 在 该 进 程 进 入 封 锁 状 态 后, 系 统 将 调 度 另 一 进 程 使 用 处 理 机, 如 果 需 要, 该 进 程 也 可 以 执 行 临 界 区 程 序, 不 会 受 到 任 何 阻 拦, 所 以 在 这 种 情 况 下, 开、 关 中 断 不 能 实 施 临 界 区 互 斥。

(3) 如 果 临 界 区 比 较 长, 则 本 法 会 降 低 中 断 响 应 速 度。

(4) 这 是 一 把 锁 处 理 各 类 临 界 区, 不 必 要 地 扩 大 了 互 斥 范 围。



  linux的实时进程有两种调度策略,SCHED_FIFO和SCHED_RR,SCHED_FIFO是简单的队列调度,并且没有timeslice的限制,

谁先来谁运行,除非是阻塞或者主动yield,否者将一直占用CPU,即使关中断也不能阻止优先级高的进程被调度运行。





你可能感兴趣的:(spin_lock_irqsave关中断后,为什么要再禁止抢占呢,不多余吗?)