0
  • 聊天消息
  • 系统消息
  • 评论与回复
登录后你可以
  • 下载海量资料
  • 学习在线课程
  • 观看技术视频
  • 写文章/发帖/加入社区
创作中心

完善资料让更多小伙伴认识你,还能领取20积分哦,立即完善>

3天内不再提示

基于Linux 软中断机制以及tasklet、工作队列机制分析

马哥Linux运维 2018-01-15 12:55 次阅读

软中断分析最近工作繁忙,没有时间总结内核相关的一些东西。上次更新博客到了linux内核中断子系统。这次总结一下软中断,也就是softirq。之后还会总结一些tasklet、工作队列机制。

1.为什么要软中断

编写驱动的时候,一个中断产生之后,内核在中断处理函数中可能需要完成很多工作。但是中断处理函数的处理是关闭了中断的。也就是说在响应中断时,系统不能再次响应外部的其它中断。这样的后果会造成有可能丢失外部中断。于是,linux内核设计出了一种架构,中断函数需要处理的任务分为两部分,一部分在中断处理函数中执行,这时系统关闭中断。另外一部分在软件中断中执行,这个时候开启中断,系统可以响应外部中断。

关于软件中断的理论各种书籍都有介绍,不多叙述。而要真正体会软件中断的作用就必须从代码的角度来分析。我们做工作时候讲求的是professional,当一个人在某个领域一无所知的时候,我们称他为小白,偶,非苹果电脑。小白的脑子里充满了各种问题。慢慢的当这些疑惑解释完之后,小白就脱白了。此时,我们对这个领域的基本框架有了解,但这和professional还有一定的差距。再加以时日,逐渐融会贯通该领域才能达到专业的境界。

2. 什么时候触发处理软件中断

说了这么多废话,赶快步入正题。初识软中断,脑子里肯定有不少的疑问,首先就是软件中断在什么地方被触发处理?这个问题的答案就是:一个硬件中断处理完成之后。下面的函数在处理完硬件中断之后推出中断处理函数,在irq_exit中会触发软件中断的处理。

基于Linux 软中断机制以及tasklet、工作队列机制分析

这里要注意,invoke_softirq必须满足两个条件才能被调用到,一个就是不是在硬件中断处理过程中或者在软件中断处理中,第二个就是必须有软件中断处于pending状态。第二个好理解,有软件中断产生才去处理,没有就不处理。第一个就不好理解了。

基于Linux 软中断机制以及tasklet、工作队列机制分析

在linux系统的进程数据结构里,有这么一个数据结构

#define preempt_count()(current_thread_info()->preempt_count),

利用preempt_count可以表示是否处于中断处理或者软件中断处理过程中。

基于Linux 软中断机制以及tasklet、工作队列机制分析

基于Linux 软中断机制以及tasklet、工作队列机制分析

preempt_count的8~23位记录中断处理和软件中断处理过程的计数。如果有计数,表示系统在硬件中断或者软件中断处理过程中。系统这么设计是为了避免软件中断在中断嵌套中被调用,并且达到在单个CPU上软件中断不能被重入的目的。对于ARM架构的CPU不存在中断嵌套中调用软件中断的问题,因为ARM架构的CPU在处理硬件中断的过程中是关闭掉中断的。只有在进入了软中断处理过程中之后才会开启硬件中断,如果在软件中断处理过程中有硬件中断嵌套,也不会再次调用软中断,because硬件中断是软件中断处理过程中再次进入的,此时preempt_count已经记录了软件中断!对于其它架构的CPU,有可能在触发调用软件中断前,也就是还在处理硬件中断的时候,就已经开启了硬件中断,可能会发生中断嵌套,在中断嵌套中是不允许调用软件中断处理的。Why?我的理解是,在发生中断嵌套的时候,表明这个时候是系统突发繁忙的时候,内核第一要务就是赶紧把中断中的事情处理完成,退出中断嵌套。避免多次嵌套,哪里有时间处理软件中断,所以把软件中断推迟到了所有中断处理完成的时候才能触发软件中断。

3. 软件中断的处理过程

之前我已经说到,软中断的一个很大的目的就是避免中断处理中,处理的操作过多而丢失中断。同时中断还需要考虑到一件事情就是中断处理过程过长就会影响系统响应时间。如果一个中断处理一秒钟,那你一定能感受到串口卡住的现象。从另外一方面说呢,我们又必须考虑中断处理的操作一定的优先度,毕竟是硬件触发的事务,关系到网络、块设备的效率问题。Linux内核就中断方面就必须考虑平衡这三个方面的问题。而下面我要分析的__do_softirq函数就恰似在这三者之间打太极,游刃有余,面面俱到!

基于Linux 软中断机制以及tasklet、工作队列机制分析

基于Linux 软中断机制以及tasklet、工作队列机制分析

__do_softirq函数处理软件中断过程如下图流程分析

4. 首先调用local_softirq_pending函数取得目前有哪些位存在软件中断

5. 调用__local_bh_disable关闭软中断,其实就是设置正在处理软件中断标记,在同一个CPU上使得不能重入__do_softirq函数

6. 重新设置软中断标记为0,set_softirq_pending重新设置软中断标记为0,这样在之后重新开启中断之后硬件中断中又可以设置软件中断位。

7. 开启硬件中断

8. 之后在一个循环中,遍历pending标志的每一位,如果这一位设置就会调用软件中断的处理函数。在这个过程中硬件中断是开启的,随时可以打断软件中断。这样保证硬件中断不会丢失。

9. 之后关闭硬件中断,查看是否又有软件中断处于pending状态,如果是,并且在本次调用__do_softirq函数过程中没有累计重复进入软件中断处理的次数超过10次,就可以重新调用软件中断处理。如果超过了10次,就调用wakeup_softirqd();唤醒内核的一个进程来处理软件中断。设立10次的限制,也是为了避免影响系统响应时间。

4. 处理软中断内核线程

之前我说到不能让CPU长时间来处理中断事务,这样会影响系统的响应时间,严重影响用户和系统之间的交互式体验。所以在之前的__do_softirq中最多将循环执行10次,那么当执行了10次仍然有软中断在pending状态,这个时候应该怎么处理呢?系统将唤醒一个软件中断处理的内核进程,在内核进程中处理pending中的软件中断。这里要注意,之前我们分析的触发软件中断的位置其实是中断上下文中,而在软中断的内核线程中实际已经是进程的上下文。

这里说的软中断上下文指的就是系统为每个CPU建立的ksoftirqd进程。

看完这个函数,我不得不佩服这个函数设计的精巧!而我更多的从中体会到其中蕴藏的一种做人的道理。那就是做人要霸道一点,太谦和太恭维不行,但是又不能横行霸道,原则的问题要公平讲理,一定的时候顾及别人的利益,好处不能一个人独吞。这就跟下面ksoftirqd处理过程一样,该狠的时候禁止抢占,其它进程别想调度到哦,但是自己占用CPU时间过长的话,也自觉的问一问是不是该释放CPU给其它进程了。

下面我们就来分析一下这个处理过程怎么就体现了上面的这种说法呢?软中断的内核进程中主要有两个大循环,外层的循环处理有软件中断就处理,没有软件中断就休眠。内层的循环处理软件中断,并每循环一次都试探一次是否过长时间占据了CPU,需要调度释放CPU给其它进程。具体的操作在注释中做了解释。

基于Linux 软中断机制以及tasklet、工作队列机制分析

基于Linux 软中断机制以及tasklet、工作队列机制分析

声明:本文内容及配图由入驻作者撰写或者入驻合作网站授权转载。文章观点仅代表作者本人,不代表电子发烧友网立场。文章及其配图仅供工程师学习之用,如有内容侵权或者其他违规问题,请联系本站处理。 举报投诉
  • Linux
    +关注

    关注

    87

    文章

    10986

    浏览量

    206718
  • 软中断
    +关注

    关注

    0

    文章

    8

    浏览量

    2983

原文标题:Linux 软中断机制分析

文章出处:【微信号:magedu-Linux,微信公众号:马哥Linux运维】欢迎添加关注!文章转载请注明出处。

收藏 人收藏

    评论

    相关推荐

    Linux驱动开发-内核共享工作队列

    工作队列里,我们把推后执行的任务叫做工作(work),描述它的数据结构为work_struct,这些工作队列结构组织成工作队列(work
    的头像 发表于 09-17 15:03 1062次阅读

    Linux 机制分析

    走入 Linux 的殿堂已经有一年有余了,在这里我想将 Linux 的各种实现机制分析一遍,一方面对自己来说也是温故而知新,另一方面,促进大家的交流,最好能够给大家一些抛砖引玉的启迪。
    发表于 05-21 09:51

    芯灵思SinlinxA33开发板Linux内核 tasklet 机制(附实测代码)

    ,工作队列中断机制实现。实际上是把耗时事件推后执行,不在中断程序执行。什么是tasklet
    发表于 02-15 15:29

    芯灵思SinlinxA64开发板Linux内核tasklet机制(附实测代码)

    ,工作队列中断机制实现。实际上是把耗时事件推后执行,不在中断程序执行。什么是tasklet
    发表于 03-12 16:45

    内核工作队列workqueue简单使用

    内核工作队列workqueue 简述
    发表于 06-11 09:30

    利用进程上下文来执行中断处理中耗时的任务

    Workqueue 工作队列是利用内核线程来异步执行工作任务的通用机制,利用进程上下文来执行中断处理中耗时的任务,因此它允许睡眠。而 Softirq 和
    发表于 01-10 06:14

    迅为STM32MP157开发板中断下文之tasklet

    tasklet 3、工作队列(work queues)我们主要讲 tasklet。调用 tasklet 以后,tasklet 绑定的函数并
    发表于 03-28 10:10

    一种高效的磁盘队列I/O机制

    分析了传统磁盘队列的存储管理开销和读写性能,针对磁盘队列I/O已成为影响消息服务器性能的首要瓶颈,提出了一种高效磁盘队列I/O机制—Flas
    发表于 05-14 19:51 32次下载

    linux kernel工作队列及源码解析

    1. 前言 工作队列(workqueue)的Linux内核中的定义的用来处理不是很紧急事件的回调方式处理方法。 以下代码的linux内核版本为2.6.19.2, 源代码文件主要为kernel
    发表于 10-27 10:19 0次下载

    Linux 2.4.x内核软中断机制

    本文从Linux内核几种软中断机制相互关系和发展沿革入手,分析了这些机制的实现方法,给出了它们的基本用法。 软
    发表于 11-02 11:01 0次下载

    你知道linux工作队列

    Linux中的Workqueue机制就是为了简化内核线程的创建。通过调用workqueue的接口就能创建内核线程。并且可以根据当前系统CPU的个数创建线程的数量,使得线程处理的事务能够并行化。
    发表于 04-26 16:49 1017次阅读
    你知道<b class='flag-5'>linux</b>的<b class='flag-5'>工作队列</b>?

    你了解过Linux内核的的tasklet机制工作队列

    Tasklet的特点,也是tasklet的精髓就是:tasklet不能休眠,同一个tasklet不能在两个CPU上同时运行,但是不同tasklet
    发表于 05-14 13:41 2571次阅读
    你了解过<b class='flag-5'>Linux</b>内核的的<b class='flag-5'>tasklet</b><b class='flag-5'>机制</b>和<b class='flag-5'>工作队列</b>?

    ZWave中的消息队列机制是什么

    这篇文章就来看看 ZWave 中是通过什么机制为我们提供了一个便捷的消息队列处理机制
    的头像 发表于 02-14 13:41 497次阅读
    ZWave中的消息<b class='flag-5'>队列</b><b class='flag-5'>机制</b>是什么

    Liteos-a内核工作队列的实现原理分析及经验总结——芯海科技PPG芯片CS1262接入OpenHarmony实战

    摘要OpenHarmony系统中使用了liteos-m、liteos-a、linux三种内核,工作队列linux内核引入的一种异步处理机制。本文对liteos-a内核下
    的头像 发表于 04-26 09:26 1334次阅读
    Liteos-a内核<b class='flag-5'>工作队列</b>的实现原理<b class='flag-5'>分析</b>及经验总结——芯海科技PPG芯片CS1262接入OpenHarmony实战

    Linux 6.9-rc1发布,加入定时器、工作队列及AMD P-State优化

    在内核方面,6.9版本进行了定时器的大幅重构,增加了每个CPU核心的时间轮支持,以提升定时器运效率,尤其在网络应用中表现出色。此外,工作队列子系统新增BH工作队列支持,摒弃了老旧的tasklet
    的头像 发表于 03-25 13:49 139次阅读