《Linux内核设计与实现》 第三章学习笔记
一、进程
2、分配进程描述符

- 每个任务的thread_info 结构在色的内核栓的尾端分配。结构中task 域中存放的是指向该任务实际task_struct 的指针。
- 进程描述符的存放内核通过一个唯一的进程标识值(process identification value)或PID 来标识每个进程。PID 是一个数,表示为pid_t 隐含类型,实际上就是一个int类型。
- 在内核中,访问任务通常需要获得指向其task_struct 的指针,有的硬件体系结构可以拿出一个专门寄存器来存放指向当前进程task_struct的指针,用于加快访问速度。
3、进程状态进程描述符中的state域描述了进程的当前状态。该域的值也必为下列五种状态标志之:

4、进程上下文当一个程序调执行了系统调用或者触发了某个异常,它就陷入了内核空间。此时,我们称内核“代表进程执行”并处于进程上下文中。
5、进程家族树所有的进程都是PID 为1 的init 进程的后代。内核在系统启动的最后阶段启动init 进程。该进程读取系统的初始化脚本( initscript)并执行其他的相关程序,最终完成系统启动的整个过程。系统中的每个进程必有一个父进程, 相应的,每个进程也可以拥有零个或多个子进程。拥有同一个父进程的所有进程被称为兄弟。每个task_struct 都包含一个指向其父进程tast_struct、叫做parent 的指针,还包含一个称为children 的子进程链表。所以,对于当前进程, 可以通过下面的代码在得其父进程的进程描述符:structtaskstruct*my_parent = current- >parent;对于给定的进程,获取链表中的下一个进程:list_entry(task->tasks.next , struct task_ s truct, tasks)在取前一个进程的方撞与之相同:list_ entry(task->tasks. prev, s truct task_ struct, tasks)
三、进程创建Unix
1、采用了与众不同的实现方式,分解到两个单独的函数中去执行:fork() 和exec().首先, fork()通过拷贝当前进程创建一个子进程。子进程与父进程的区别仅仅在于PID(每个进程唯一)、PPID (父进程的进程号,子进程将其设置为被拷贝进程的PID )和某些资源和统计量(例如,挂起的信号,它没有必要被继承)。exec()函数负责读取可执行文件并将其载入地址空间开始运行。3.3.1 写时拷贝传统的fork()系统调用直接把所有的资源复制给新创建的进程。Linux 的fork()使用写时拷贝( copy-on-write)页实现。
2、只有在需要写入的时候,数据才会被复制,从而使各个进程拥有各自的拷贝。fork()的实际开销就是复制父进程的页表以反给予进程创建唯一的进程描述符。
3、fork()Linux 通过clone()系统调用实现fork() 。这个调用通过一系列的参数标志来指明父、子进程需要共享的资源。fork()、vfork()和clone()库函数都根据各自需要的参数去调用clone(),然后由clone()去调用do_fork()。do_fork 完成了创建中的大部分工作,它的定义在kemeVfork.c 文件中。该函数调用copy_process()函数,然后让进程开始运行。
- 1)在调用copy_process()时, task_struct 的vfor_done 成员被设置为NULL 。
- 2)在执行do_fork()时,如果给定特别标志,则vfork_done 会指向一个特定地址。
- 3)子进程先开始执行后,父进程不是马上恢复执行,而是一直等待,直到子进程通过vfork_done 指针向它发送信号。
- 4) 在调用mm_release()时,该函数用于进程退出内存地址空间, 并且检查vfork_done 是否为空,如果不为空,则会向父进程发送信号。
- 5)回到do_fork(),父进程醒来并返回。
- clone(CLONE_VMclone_CLONE_FILBSCLONE_SIGHAND )
- 递给clone()的参数标志决定了新创建进程的行为方式和父子进程之间共享的资源种类
3、内核线程内核经常需要在后台执行一些操作。这种任务可以通过内核线程( kernel thread)完成一独立运行在内核空间的标准进程。
- 1)将tast_struct 中的标志成员设置为PF_EXITING
- 2)调用del_timer_ sync()删除任一内核定时器。根据返回的结果,它确保没有定时器在排队,也设有定时器处理程序在运行。
- 3)如果BSD 的进程记账功能是开启的, do_exit()调用acct_update_ integrals()来输出记账信息。
- 4)然后调用exit_mm()函数释放进程占用的mm_struct,如果没有别的进程使用它们(也就是说,这个地址空间没有被共享),就彻底释放它们。
- 5) 接下来调用sem_ exit()函数。如果进程排队等候IPC 信号,它则离开队列。
- 6)调用exit_files()和exit_fs(),以分别递藏文件描述符、文件系统数据的引用计数。如果其中某个引用计数的数值降为零,那么就代表没有进程在使用相应的资源,此时可以释放。
- 7)接着把存放在task_struct 的exit_code 成员中的任务退出代码置为由exit()提供的退出代码,或者去完成任何其他由内核机制规定的退出动作。退出代码存放在这里供父进程随时检索。
- 8)调用exit_notify()向父进程发送信号,给子进程重新找养父,养父为钱程组中的其他钱程或者为init 进程,并把进程状态(存放在task_struct 结构的exit_state 中〉设成EXIT_ZOMBIE 。
- 9) do_exit()调用schedule()切换到新的进程。因为处EXIT_ZOMBIE 状态的进程不会再被调度,所以这是进程所执行的最后一段代码。do_exit()永不返回。
- 1)它调用一exit_signal(),该函数调用_unhash proc(),后者又调用detach_pid()从pidhash上删除该进程,同时也要从任务列表中删除该进程。
- 2) _exit_sal()释放目前僵死进程所使用的所有剩余资源,并进行最终统计和记录。
- 3)如果这个进程是钱程组最后一个进程,并且领头进程已经死掉,那么release_task()就要通知僵死的领头进程的父进程.的release_task()调用put_task_ struct()辑放进程内核和read_info 结构所占的页,并释放tast_struct 所占的slab 高速缓存。
《Linux内核设计与实现》 第三章学习笔记的更多相关文章
- LINUX内核设计与实现第三周读书笔记
LINUX内核设计与实现第三周读书笔记 第一章 LINUX内核简介 1.1 Unix的历史 1969年的夏天,贝尔实验室的程序员们在一台PDR-7型机上实现了Unix这个全新的操作系统. 1973年, ...
- Linux内核设计与实现 第三章
1. 进程和线程 进程和线程是程序运行时状态,是动态变化的,进程和线程的管理操作都是由内核来实现的. Linux中的进程于Windows相比是很轻量级的,而且不严格区分进程和线程,线程不过是一种特殊的 ...
- 《Linux内核分析》之第三章读书笔记
进程管理 进程是处于执行期的程序以及相关的资源的总称,也称作任务.执行线程,简称线程,是在进程中活动的对象. 可以两个或两个以上的进程执行同一个程序 也可以两个或两个以上并存的进程共享许多资源 内核调 ...
- 《Linux内核设计与实现》第四周读书笔记——第五章
<Linux内核设计与实现>第四周读书笔记--第五章 20135301张忻 估算学习时间:共1.5小时 读书:1.0 代码:0 作业:0 博客:0.5 实际学习时间:共2.0小时 读书:1 ...
- linux及安全《Linux内核设计与实现》第一章——20135227黄晓妍
<linux内核设计与实现>第一章 第一章Linux内核简介: 1.3操作系统和内核简介 操作系统:系统包含了操作系统和所有运行在它之上的应用程序.操作系统是指整个在系统中负责完成最基本功 ...
- 《Linux内核设计与实现》Chapter 3 读书笔记
<Linux内核设计与实现>Chapter 3 读书笔记 进程管理是所有操作系统的心脏所在. 一.进程 1.进程就是处于执行期的程序以及它所包含的资源的总称. 2.线程是在进程中活动的对象 ...
- 《Linux内核设计与实现》Chapter 1 读书笔记
<Linux内核设计与实现>Chapter 1 读书笔记 一.Unix的特点 Unix从Multics中产生,是一个强大.健壮和稳定的操作系统. 特点 1.很简洁 2.在Unix系统中,所 ...
- 《Linux内核设计与实现》Chapter 2 读书笔记
<Linux内核设计与实现>Chapter 2 读书笔记 一.获取内核源码 1.使用Git 我们曾经在以前的学习中使用过Git方法 $ git clone git://git.kernel ...
- 《Linux内核设计与实现》Chapter 5 读书笔记
<Linux内核设计与实现>Chapter 5 读书笔记 在现代操作系统中,内核提供了用户进程与内核进行交互的一组接口,这些接口的作用是: 使应用程序受限地访问硬件设备 提供创建新进程与已 ...
- 《Linux内核设计与实现》Chapter 18 读书笔记
<Linux内核设计与实现>Chapter 18 读书笔记 一.准备开始 一个bug 一个藏匿bug的内核版本 知道这个bug最早出现在哪个内核版本中. 相关内核代码的知识和运气 想要成功 ...
随机推荐
- 建立标准编码规则(三)-CodeFixProvider 给代码分析器增加修复建议
给代码分析器增加修复建议 既然代码分析器,向代码编写者提出了错误或警告,那么有没有可能向代码编写者提交有效的改进建议? 相对于 DiagnosticAnalyzer,代码修复继承与 CodeFixPr ...
- vue 去除前后空格trim
一.使用trim修饰符 <input v-model.trim = "massage" > 二.使用filter过去属性 html: <ul id="l ...
- IO_ObjectOutputStream(对象的序列化)
对象序列化就是将一些对象写入到硬盘中存储起来,以便下次复用 import java.io.FileInputStream; import java.io.FileOutputStream; impor ...
- WPFの数据源事件变更通知
如果数据绑定的目标是TextBox元素的Text属性,那么默认会使用双向绑定(Mode.TwoWay),此时用户可以通过更改TextBox元素Text属性的值从而更新源属性信息,但是如果在程序代码中更 ...
- WPFの获取任意元素的位置
如果布局在Grid中: 方法一: //_stackPanel为子元素,_grid为父元素 Point point = _stackPanel.TranslatePoint(new Point(0, 0 ...
- ESP-手机--双向通信模式
1 AP 接受手机 2 STA(密码固定)连接路由器,AP接受手机 3 STA(密码灵活)连接路由器,AP接受手机 1 AP 接受手机 #include <ESP8266WiFi.h> ...
- 【JDK和Open JDK】平常使用的JDK和Open JDK有什么区别(转)
文章转自https://www.cnblogs.com/sxdcgaq8080/p/7487369.html 注意到这个问题,是在CentOS7上安装JDK的时候,查找相关的资料,发现安装JDK之前都 ...
- Druid加密
至于为什么加密,主要防止一些过多人知道数据库密码,可能造成公司的损失,同时也避免一些潜在的危害,因此,数据库密码最好还是只有几个人知道,太多人知道的话,影响不好. 最近删库的事情,太多了,个人觉得一个 ...
- Linux系统中将普通用户添加到sudoers
我们经常会在普通用户下用到sudo命令,为了不用频繁切换root用户,我们可以将普通用户添加到sudoers里面.Linux默认是没有将用户添加到sudoers列表中的,需要root手动将账户添加到s ...
- PAT A1138 Postorder Traversal (25 分)——大树的遍历
Suppose that all the keys in a binary tree are distinct positive integers. Given the preorder and in ...