linux内核调度问题分析
目录
一、调度场景分析
不支持内核抢占的内核
支持内核抢占
二、如何让新进程执行
三、调度的本质
一、调度场景分析
假如内核只有3个线程,线程0创建线程1和线程2.当系统时钟到来时,时钟中断处理函数会检查是否有进程需要调度。当有进程需要调度时,调度器会选择线程1或者线程2。
执行流程:start_kernel运行在线程0里,线程0创建线程1和线程2。函数调用关系start_kernel()->kernel_debug()->do_fork 创建新线程,并把新线程添加到调度器的就绪队列中。线程0创建线程1和线程2后,进入while线程,线程0不会退出,等待被调度出去。
1、产生时钟中断。处理器采用定时器来周期性地执行。调度器利用时钟中断来定时检测当前运行的线程是否需要调度。当需要调度时,设置need_resched标志位
2、当时钟中断返回,根据linux内核是否支持内核抢占来确定是否需要调度:
不支持内核抢占的内核
不会检查是否调度。即使线程0的need_resched标志位置位了,linux内核也不会调度线程1或者线程2。只有发生在用户态的中断返回或者系统调用返回用户空间时,才会检查是否需要调度。
1)发生时钟中断。触发时钟中断时 当前进程有可能在用户态执行,也可能在内核态执行。
如果进程运行在用户态发生了中断,那么会进入异常向量表的el0_irq汇编函数;
如果进程运行在内核态时发生了中断,会进入异常向量表的el1_irq汇编函数中。
进入中断时,CPU会自动关闭中断。
2)在el1_irq汇编函数里,首先会保存中断现场到当前进程的栈中,使用pt_regs数据结构来实现pt_regs栈,保存中断现场。
中断处理程序过程包括切换到linux内核中断栈、硬件中断号的查询、中断服务程序处理等
3)当确定中断源时时钟中断后,scheduler_tick()函数会检查当前进程是否需要调度。如果需要调度,设置当前进程need_resched标志位(TIF_NEED_RESCHED),
4)中断返回。这里需要给中断控制器返回一个中断结束信号
5)在el1_irq汇编函数恢复中断现场。2)的对应操作
在不支持内核抢占的系统里,汇编函数不会检查是否需要调度。在返回时,CPU打开中断,然后从中断的地方继续执行线程0
支持内核抢占
1)中断返回会检查当前进程是否设置了need_resched表示位,如果置位,调用preempt_schedule_irq函数以调度其他进程并运行。
2)在el1_irq汇编函数即将返回中断现场时,判断当前进程是否需要调度。如果需要调度,调度器会选择下一个进程,并且进行进程的切换。
3)如果选择现场1,则从线程1的pt_regs中恢复中断现场并打开中断,然后继续执行内核线程1的代码。
二、如何让新进程执行
如果线程1是新创建的,它的栈应该是空的,第一次运行时如何恢复中断现场呢?如果不能从线程1的栈中恢复中断现场,那是不是线程1一直在关闭中断的状态下运行?
对于内核线程来说,在创建时会对如下两部分内容进行设置与保存。copy_thread()函数
- 进程的硬件上下文。保存在进程的cpu_context数据结构。
- pt_regs
int copy_thread_tls(unsigned long clone_flags, unsigned long stack_start,unsigned long stk_sz, struct task_struct *p, unsigned long tls)
{} else {memset(childregs, 0, sizeof(struct pt_regs));childregs->pstate = PSR_MODE_EL1h;//5 处理器状态 第0位 栈指针选择符,1:选择栈之战寄存器SP_EL1 2:3 异常级别,值1表示异常级别1if (IS_ENABLED(CONFIG_ARM64_UAO) &&cpus_have_const_cap(ARM64_HAS_UAO))childregs->pstate |= PSR_UAO_BIT;if (arm64_get_ssbd_state() == ARM64_SSBD_FORCE_DISABLE)set_ssbs_bit(childregs);if (system_uses_irq_prio_masking())childregs->pmr_save = GIC_PRIO_IRQON;p->thread.cpu_context.x19 = stack_start;//函数地址,用来创建内核线程的函数kernel_thread的第一参数p->thread.cpu_context.x20 = stk_sz;//参数 ,用来创建内核线程的函数kernel_thread的第二参数}p->thread.cpu_context.pc = (unsigned long)ret_from_fork;//子进程的程序计数器,调度入口p->thread.cpu_context.sp = (unsigned long)childregs;//sp指向内核栈底部pt_regs起始位置}
stack_start指向内核线程的回调函数
x20 指向回调函数的参数
PC寄存器 ret_from_fork 执行入口
三、调度的本质
系统中有一个用户进程A和一个内核线程B,在不考虑自愿调度和系统调用情况下,请描述这两个进程是如何相互切换并运行的。
- 进程A在用户空间运行;
- 发生中断
- CPU打断正在运行的用户进程A,处于异常模式。CPU会跳转到异常向量表的el0_irq里。在汇编函数el0_irq中,首先把中断现场保存到进程A的pt_regs栈
- 处理中断
- 调度滴答处理函数,返回el0_irq汇编函数里。即将返回现场前,ret_to_user汇编函数会检查当前进程是否需要调度。
- 若当前进程需要调度,调用schedule()函数选择下一个进程并切换 ;(switch_to函数)
- 切换函数返回,CPU开始运行内核线程B;进程需要为前一个进程做收尾工作,比如调用raw_spin_unlock_irq来释放锁并打开本地中断。见finish_task_switch函数。
- CPU沿着内核线程B保存的栈帧回溯,一直返回。返回路径finish_task_switch->el1_preempt->el1_irq
- 在el1_irq汇编函数里把上一次发生中断时保存在栈里的中断现场进行恢复,最后从上一次中断的地方开始执行内核线程B的代码。
以上涉及两个上下文切换,中断上下文(pt_regs),进程上下文(task_struct)
相关文章:
linux内核调度问题分析
目录 一、调度场景分析 不支持内核抢占的内核 支持内核抢占 二、如何让新进程执行 三、调度的本质 一、调度场景分析 假如内核只有3个线程,线程0创建线程1和线程2.当系统时钟到来时,时钟中断处理函数会检查是否有进程需要调度。当有进程需要调度时…...
C语言-基础了解-25-C强制类型转换
C强制类型转换 一、强制类型转换 强制类型转换是把变量从一种类型转换为另一种数据类型。例如,如果您想存储一个 long 类型的值到一个简单的整型中,您需要把 long 类型强制转换为 int 类型。您可以使用强制类型转换运算符来把值显式地从一种类型转换为…...
【Python】如何安装 Allure 工具进行自动化测试
Allure 是一种流行的工具,用于以人类可读的格式生成测试报告,从而更容易理解和分析测试结果。在这篇博客中,我们将探索如何在 Windows 机器上安装 Allure 及其依赖项。 1 Prerequisites 先决条件 在田辛老师开始之前,请确保您的…...
nginx七大核心应用场景详解 解决生产中的实际问题 二次开发扩展
nginx七大核心应用场景详解 & 解决生产中的实际问题1、nginx的安装与简单配置1.1、环境准备1.2、nginx基本操作指令:1.3、安装成系统服务1.4、conf 配置文件说明2、虚拟主机2.1、nginx多主机配置2.2、二级域名与短网址解析3、基于反向代理的负载均衡3.1、跳转到…...
Java 整合 Redis
文章目录Java 整合 Redis一、Jedis二、Spring-Data-RedisJava 整合 Redis Redis 在项目中我们主要用来做缓存,就像我们用 MySQL 做持久层数据一样。Redis 的客户端有两种实现方式: 一是直接调用 Jedis 来实现,类似于 Java 使用 JDBC 操作数…...
Django实践-03模型-02基于admin管理表
文章目录Django实践-03模型利用Django后台管理模型1. 将admin应用所需的表迁移到数据库中。2. 创建访问admin应用的超级用户账号,3. 运行项目4.注册模型类5.对模型进行CRUD操作。6.实现学科页和老师页效果1. 修改polls/views.py文件。2.修改templates/polls/subject…...
如何安装python
windows安装 下载安装包 登录python官网 https://www.python.org/ 点击downloads 置顶下载的是最新的python版本 如果想下载指定版本往下翻找 安装程序 点击即可下载,然后打开下载的exe程序 勾选添加pythonexec到path,也就是添加到环境变量 使用a…...
java String类 万字详解(通俗易懂)
目录 一、前言 二、介绍和溯源 三、String类常用构造器 1.String() 2.String(byte[] bytes) 3.String(char[] value) 4.String(char[] value, int offset, int count) 5.String(String original) Δ演示 : 四、不同方式创建String类对象的区别 1.直接赋值的方式 2.常规new…...
Hive拉链表
概述 拉链表:维护历史状态以及最新状态数据的表 作用场景 1. 数据量比较大。 2. 表中的部分字段会被更新,比如用户的地址,银行利率,订单的状态等。 3. 需要查看某一个时间点或者时间段的历史快照信息,比如,…...
day1 开发我的第一个MyBatis程序
文章目录开发我的第一个MyBatis程序1. resources目录:2. 开发步骤3. 从 XML 中构建 SqlSessionFactoryMyBatisIntroductionTest4. mybatis中有两个主要的配置文件:5. 关于第一个程序的小细节mybatis-config.xml6. 关于mybatis的事务管理机制。࿰…...
【CDP】更改solr 存储路径导致ranger-audit 大量报错问题解决
前言 我们生产上公司是使用的CDP集群,一次管理员通知,Solr 组件的数据存放路径磁盘空间不够。 我们的solr 组件时为 Ranger 服务提供日志审计功能, 在我们更改了磁盘路径,并重启了Solr 组件,然后发现相关组件&#…...
JavaScript基础一、简介
零、文章目录 文章地址 个人博客-CSDN地址:https://blog.csdn.net/liyou123456789个人博客-GiteePages:https://bluecusliyou.gitee.io/techlearn 代码仓库地址 Gitee:https://gitee.com/bluecusliyou/TechLearnGithub:https:…...
Qt音视频开发20-vlc内核动态保存录像文件(不需要重新编译源码)
一、前言 在vlc默认提供的保存文件方式中,通过打开的时候传入指定的参数来保存文件,直到关闭播放生成文件,这种方式简单暴力,但是不适用大部分的场景,大部分时候需要的是提供开始录制和停止录制的功能,也就…...
【深度学习】BERT变体—RoBERTa
RoBERTa是的BERT的常用变体,出自Facebook的RoBERTa: A Robustly Optimized BERT Pretraining Approach。来自Facebook的作者根据BERT训练不足的缺点提出了更有效的预训练方法,并发布了具有更强鲁棒性的BERT:RoBERTa。 RoBERTa通过以下四个方面…...
java面试准备1
JVM、JRE和JDK的关系 JVM:Java Virtual Machine是java虚拟机,Java程序需要运行在虚拟机上,不同的平台有自己的虚拟机,因此java可以实现跨平台使用。 JRE:Java Runtion Envirement包括Java虚拟机和Java程序所需要的核心类库等。 J…...
buffer它到底做了个啥,源码级分析linux内核的文件系统的缓冲区
最近一直在学习linux内核源码,总结一下 https://github.com/xiaozhang8tuo/linux-kernel-0.11 自己整理过的带注释的源码。 为什么要有buffer 高速缓冲区是文件系统访问块设备中数据的必经要道(PS:如果所有程序结果都不落盘,只是int a, a直接在主存…...
【蓝桥杯刷题】盗版Huybery系列之手抓饼赛马
【蓝桥杯刷题】—— 盗版Huybery系列之手抓饼赛马😎😎😎 目录 💡前言🌞: 💛盗版Huybery系列之手抓饼赛马题目💛 💪 解题思路的分享💪 😊题…...
【微信小程序-原生开发】实用教程16 - 查看详情(含页面跳转的传参方法--简单传参 vs 复杂传参)
需在实现列表的基础上开发 【微信小程序-原生开发】实用教程15 - 列表的排序、搜索(含云数据库常用查询条件的使用方法,t-search 组件的使用)_朝阳39的博客-CSDN博客 https://sunshinehu.blog.csdn.net/article/details/129356909 效果预览 …...
论文精读:Ansor: Generating High-Performance Tensor Programs for Deep Learning
文章目录1. Abstract2. Introduction3. Background4. Design Overview5. Program Sampling5.1 Sketch Generation5.2 Random Annotation6. Performance Fine-tuning6.1 Evolutionary Search6.2 Learned Cost Model7. Task Scheduler7.1 Problem Formulation7.2 Optimizing with…...
SpringBoot With IoC,DI, AOP,自动配置
文章目录1 IoC(Inverse Of Controller)2 DI(Dependency Injection)3 AOP(面向切面编程)3.1 什么是AOP?3.2 AOP的作用?3.3 AOP的核心概念3.4 AOP常见通知类型3.5 切入点表达式4 自动配…...
国防科技大学计算机基础课程笔记02信息编码
1.机内码和国标码 国标码就是我们非常熟悉的这个GB2312,但是因为都是16进制,因此这个了16进制的数据既可以翻译成为这个机器码,也可以翻译成为这个国标码,所以这个时候很容易会出现这个歧义的情况; 因此,我们的这个国…...
在HarmonyOS ArkTS ArkUI-X 5.0及以上版本中,手势开发全攻略:
在 HarmonyOS 应用开发中,手势交互是连接用户与设备的核心纽带。ArkTS 框架提供了丰富的手势处理能力,既支持点击、长按、拖拽等基础单一手势的精细控制,也能通过多种绑定策略解决父子组件的手势竞争问题。本文将结合官方开发文档,…...
Psychopy音频的使用
Psychopy音频的使用 本文主要解决以下问题: 指定音频引擎与设备;播放音频文件 本文所使用的环境: Python3.10 numpy2.2.6 psychopy2025.1.1 psychtoolbox3.0.19.14 一、音频配置 Psychopy文档链接为Sound - for audio playback — Psy…...
.Net Framework 4/C# 关键字(非常用,持续更新...)
一、is 关键字 is 关键字用于检查对象是否于给定类型兼容,如果兼容将返回 true,如果不兼容则返回 false,在进行类型转换前,可以先使用 is 关键字判断对象是否与指定类型兼容,如果兼容才进行转换,这样的转换是安全的。 例如有:首先创建一个字符串对象,然后将字符串对象隐…...
Pinocchio 库详解及其在足式机器人上的应用
Pinocchio 库详解及其在足式机器人上的应用 Pinocchio (Pinocchio is not only a nose) 是一个开源的 C 库,专门用于快速计算机器人模型的正向运动学、逆向运动学、雅可比矩阵、动力学和动力学导数。它主要关注效率和准确性,并提供了一个通用的框架&…...
推荐 github 项目:GeminiImageApp(图片生成方向,可以做一定的素材)
推荐 github 项目:GeminiImageApp(图片生成方向,可以做一定的素材) 这个项目能干嘛? 使用 gemini 2.0 的 api 和 google 其他的 api 来做衍生处理 简化和优化了文生图和图生图的行为(我的最主要) 并且有一些目标检测和切割(我用不到) 视频和 imagefx 因为没 a…...
Java数值运算常见陷阱与规避方法
整数除法中的舍入问题 问题现象 当开发者预期进行浮点除法却误用整数除法时,会出现小数部分被截断的情况。典型错误模式如下: void process(int value) {double half = value / 2; // 整数除法导致截断// 使用half变量 }此时...
uniapp 开发ios, xcode 提交app store connect 和 testflight内测
uniapp 中配置 配置manifest 文档:manifest.json 应用配置 | uni-app官网 hbuilderx中本地打包 下载IOS最新SDK 开发环境 | uni小程序SDK hbulderx 版本号:4.66 对应的sdk版本 4.66 两者必须一致 本地打包的资源导入到SDK 导入资源 | uni小程序SDK …...
MySQL 部分重点知识篇
一、数据库对象 1. 主键 定义 :主键是用于唯一标识表中每一行记录的字段或字段组合。它具有唯一性和非空性特点。 作用 :确保数据的完整性,便于数据的查询和管理。 示例 :在学生信息表中,学号可以作为主键ÿ…...
Oracle11g安装包
Oracle 11g安装包 适用于windows系统,64位 下载路径 oracle 11g 安装包...
