Linux内核中的软中断、tasklet和工作队列详解( 六 )
以上均是采用缺省工作者线程来实现工作队列 , 其优点是简单易用 , 缺点是如果缺省工作队列负载太重 , 执行效率会很低 , 这就需要我们创建自己的工作者线程和工作队列 。
- 自定义工作队列
create_workqueue(name) //宏定义 返回值为工作队列 , name为工作线程名称 。 创建新的工作队列和相应的工作者线程 , name用于该内核线程的命名 。 int queue_work(struct workqueue_struct *wq, struct work_struct *work)//类似于schedule_work , 区别在于queue_work把给定工作提交给创建的工作队列wq而不是缺省队列 。 int queue_delayed_work(struct workqueue_struct *wq,struct delayed_work *dwork, unsigned long delay)//调度延迟工作 。 void flush_workqueue(struct workqueue_struct *wq)//刷新指定工作队列 。 void destroy_workqueue(struct workqueue_struct *wq)//释放创建的工作队列 。
实现原理- 工作队列的组织结构 即workqueue_struct、cpu_workqueue_struct与work_struct的关系 。一个工作队列对应一个work_queue_struct , 工作队列中每cpu的工作队列由cpu_workqueue_struct表示 , 而work_struct为其上的具体工作 。关系如下图所示:
文章插图
2.工作队列的工作过程
文章插图
- 应用实例 linux各个接口的状态(up/down)的消息需要通知netdev_chain上感兴趣的模块同时上报用户空间消息 。 这里使用的就是工作队列 。具体流程图如下所示:
文章插图
- 是否处于中断中在Linux中是通过preempt_count来判断的,具体如下: 在linux系统的进程数据结构里 , 有这么一个数据结构: #define preempt_count() (current_thread_info()->preempt_count) 利用preempt_count可以表示是否处于中断处理或者软件中断处理过程中,如下所示: # define hardirq_count() (preempt_count() & HARDIRQ_MASK) #define softirq_count() (preempt_count() & SOFTIRQ_MASK) #define irq_count() (preempt_count() & (HARDIRQ_MASK | SOFTIRQ_MASK | NMI_MASK)) #define in_irq() (hardirq_count()) #define in_softirq() (softirq_count()) #define in_interrupt() (irq_count())
文章插图
【Linux内核中的软中断、tasklet和工作队列详解】preempt_count的8~23位记录中断处理和软件中断处理过程的计数 。 如果有计数 , 表示系统在硬件中断或者软件中断处理过程中 。
推荐阅读
- Eyeware Beam使用iPhone追踪玩家在游戏中的眼睛运动
- 向日葵远程控制企业版客户端更新升级,优化远控UI适配SADDC内核算法
- AMD Zen3 APU内核图提前偷跑:三级缓存质变
- 苹果M1、A14内核设计对比:差别很大
- Linux Kernel 5.10.5发布:禁用FBCON加速滚动特性
- 田伟院士:我眼中的医疗机器人
- Mozilla将默认禁用Firefox中的退格键以防止用户编辑数据丢失
- Linux 5.11开始围绕PCI Express 6.0进行早期准备
- Fedora正在寻求协助 希望加快Linux 5.10 LTS内核测试进度
- Linux Mint 20.1 Ulyssa稳定版已确定延期至2021年初发布