spin_lock_bh

 一个软中断不会抢占另外一个软中断,softirq执行时preempt_count大于零,所以从中断返回到软中断的时候,不会调度

 

用lock_bh(),是因为这些netfilter hooks可以从系统调用的context到达,
比如socket的send_msg()是可以到达LOCAL_OUT/POST_ROUTING的,
这样,也就是说,在这些情况下操作conntrack链表的时候,是进程上下文,而不是软中断上下文,
因此,是需要关闭bh的。

ip_conntrack_in()比较特殊,它是注册在PRE_ROUTING上的,
按道理说,它只能从软中断到达,因此只需要spin_lock()就可以了,
之所以也使用spin_lock_bh(),
可能是为了维护一致性(这里多一次lock_bh无所谓),
也可能是因为会有些特殊的虚拟设备,可以从其他的上下文到达PRE_ROUTING。

Linux内核为将中断服务分为两部分提供了方便,并设立了相应的机制。在以前的内核中,这个机制就叫bottom half(简称bh),但在2.4版中有了新的发展和推广,叫做软中断(softirq)机制。

1.Bh机制

以前内核中的Bh机制设置了一个函数指针数组bh_base[],它把所有的后半部分都组织起来,其大小为32,数组中的每一项就是一个后半部分,即一个bh 函数。同时,又设置了两个32位无符号整数bh_active和bh_mask,每个无符号整数中的一位对应着bh_base[]中的一个元素,如图3.9所示:

 在2.4以前的内核中,每次执行完do_IRQ()中的中断服务例程以后,以及每次系统调用结束之前,就在一个叫do_bottom_half()的函数中执行相应的bh函数。

在do_bottom_half()中对bh函数的执行是在关中断的情况下进行的,也就是说对bh的执行进行了严格的“串行化”,这种方式简化了bh的设计,这是因为,对单CPU来说,bh 函数的执行可以不嵌套;而对于多CPU来说,在同一时间内最多只允许一个CPU执行bh函数。

这种简化了的设计在一定程度上保证了从单CPU到多CPU SMP结构的平稳过渡,但随着时间的推移,就会发现这样的处理对于SMP的性能有不利的影响。因为,当系统中有很多个bh函数需要执行时,bh函数的“串行化”却只能使一个CPU执行一个bh函数,其它CPU即使空闲,也不能执行其它的bh函数。由此可以看出,bh函数的串行化是针对所有CPU的,根本发挥不出多CPU的优势。

那么,在新内核的设计中,是改进bh机制还是抛弃bh机制,建立一种新的机制?2.4选择了一种折中的办法,继续保留bh机制,另外增加一种或几种机制,并把它们纳入一个统一的框架中,这就是2.4内核中的软中断(softirq)机制。

2.软中断机制

软中断机制也是推迟内核函数的执行,然而,与bh函数严格地串行执行相比,软中断却在任何时候都不需要串行化。同一个软中断的两个实例完全有可能在两个CPU上同时运行。当然,在这种情况下,软中断必须是可重入的。软中断给网络部分带来的好处尤为突出,因为2.4内核中用两个软中断代替原来的一个NET_BH函数,这就使得在多处理机系统上软中断的执行更为高效。

3.Tasklet机制

另一个类似于bh的机制叫做tasklet。Tasklet建立在软中断之上,但与软中断的区别是,同一个tasklet只能运行在一个CPU上,而不同的tasklet可以同时运行在不同的CPU上。在这种情况下,tasklet就不需要是可重入的,因此,编写tasklet比编写一个软中断要容易。

     Bh机制在2.4中依然存在,但不是作为一个单独的机制存在,而是建立在tasklet之上。因此,在2.4版中,设备驱动程序的开发者必须更新他们原来的驱动程序,用tasklet代替bh。

 

 

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值