《Linux内核与分析》第六周
20135130王川东
1、操作系统的三大管理功能包括:进程管理,内存管理,文件系统。
2、 Linux内核通过唯一的进程标识PID来区别每个进程。为了管理进程,内核必须对每个进程进行清晰的描述,进程描述符提供了内核所需了解的进程信息。每个进程的所有信息记录在了进程描述符(task_struct)中。struct task_struct数据结构很庞大,包括进程状态、进程内核堆栈、进程打开的文件、进程优先级以及进程调度相关信息等等。这是一个包含了很多信息的结构体,也被称之为进程控制块(PCB)。
3、Linux中,PCB task_struct中不包含进程包含的线程列表信息。
4、Linux进程的状态与操作系统原理中的描述的进程状态似乎有所不同,比如就绪状态和运行状态都是TASK_RUNNING。这是因为在Linux中,所谓区别一个进程的状态是就绪还是运行,在于它是否得到了CPU的控制权。也就是说,这个进程是否在CPU上实际的执行,如果有实际执行,那就是运行,如果没有,哪怕目前是可以运行,也还只是就绪状态。
注意,PCB task_struct中 存有进程链表,这是讲所有进程存在一个双向链表结构中。struct list_head tasks。
5、程序创建的进程具有父子关系,在编程时往往需要引用这样的父子关系。进程描述符中有几个域用来表示这样的关系。
6、Linux为每个进程分配一个8KB大小的内存区域,用于存放该进程两个不同的数据结构:Thread_info和进程的内核堆栈。进程处于内核态时使用, 不同于用户态堆栈,即PCB中指定了内核栈。内核控制路径所用的堆栈 很少,因此对栈和Thread_info 来说,8KB足够了
7、创建一个新进程在内核中的执行过程:fork、vfork和clone三个系统调用都可以创建一个新进程,而且都是通过调用do_fork来实现进程的创建;Linux通过复制父进程来创建一个新进程。从用户态的代码看fork();函数返回了两次,即在父子进程中各返回一次,父进程从系统调用中返回比较容易理解,子进程从系统调用中返回,那它在系统调用处理过程中的哪里开始执行的呢?Linux中,fork()系统调用产生的子进程在系统调用处理过程中从ret_from_fork处开始执行。
实验过程:
通过在myKernel中添加fork的功能,分析Linux内核创建一个新进程的过程。
添加后重新生成menu,并运行。

通过gdb调试,设置断点在sys_clone, do_fork, dup_task_struct, copy_process, copy_thread, ret_from_fork。运行menuOS中的fork,继续调试,查看断点处的代码情况
。
创建新进程的过程分析:
创建的新进程是从哪里开始执行的:ret_from_fork
*childregs = *current_pt_regs(); 复制内核堆栈(复制的pt_regs,是SAVE_ALL中系统调用压栈的那一部分。)
childregs->ax = 0; 子进程的fork返回0
p->thread.sp = (unsigned long) childregs; 调度到子进程时的内核栈顶
p->thread.ip = (unsigned long) ret_from_fork; 调度到子进程时的第一条指令地址
ip指向的是ret_from_fork,所以是从这里开始执行的。
Linux操作系统通过start_kernel,在调用的时候执行得到cpu_idle进程,后来通过kernel_init和kthreadd生成了0号进程和1号进程,分别作为最初的内核进程和用户进程。这里的进程最初是通过程序员具体在代码中设置的结构啊,信息啊之类的,而之后的进程则是复制之前的进程,这里可以看做是父进程,生成了新的进程,也就是子进程,当然,子进程的信息会有修改,它并不是跟父进程完全一样。
程序调用状态可以表示为:

fork具体工作过程:
1. 调用sys_clone
2. 执行do_fork(), fork、vfork和clone三个系统调用都可以创建一个新进程,而且都是通过调用do_fork来实现进程的创建。do_fork()负责进程的复制。
3. 执行copy_process
4 dup_task_struct,复制父进程的task_struct信息到新的task_struct里
fork会产生父子进程,在父进程中,返回值是子进程的进程号;在子进程中,返回值为0。因此可通过返回值来判断当前进程是父进程还是子进程。使用fork函数得到的子进程是父进程的一个复制品,它从父进程处复制了整个进程的地址空间,包括进程上下文,进程堆栈,内存信息,打开的文件描述符,信号控制设定,进程优先级,进程组号,当前工作目录,根目录,资源限制,控制终端等。
5.copy_thread
6.ret_from_fork
进程的用户栈的起始地址存储在task_struct结构的stack_start成员中,新进程是从ret_from_fork处开始执行的。对于fork执行处理过程来说,父子进程共享同一段代码空间,”一次调用,两次返回“,其实对于调用fork的父进程来说,如果fork出来的子进程没有得到调度,那么父进程从fork系统调用返回。再看fork出来的子进程,由 copy_process函数可以看出,子进程的返回地址为ret_from_fork(和父进程在同一个代码点上返回),返回值直接置为0。所以当子进 程得到调度的时候,也从fork返回,返回值为0。ret_from_fork()调用schedule_tail()函数,用存放在栈中的值再装入所有寄存器,并强迫CPU返回到用户态。这样,eax寄存器就装过两个值,一个是子进程的值0,一个是父进程的值——子进程的PID。然后在fork()、vfork()或clone()返回时,新进程将开始执行。在不同的进程中返回不同的值。
《Linux内核与分析》第六周的更多相关文章
- Linux内核及分析 第六周 分析Linux内核创建一个新进程的过程
实验过程 1.github上克隆相应的mengning/menu.git 2.测试menuOS,测试fork直接执行结果 3.配置调试系统,进入gdb调试,利用file linux-3.18.6/vm ...
- 2019-2020-1 20199303 《Linux内核原理分析》 第一周作业
2019-2020-1 20199303 <Linux内核原理分析> 第一周作业 1. 环境准备 在众多的Linux发行版中,Ubuntu,小红帽还有类Unix系统的BSD系统,我选择了目 ...
- Linux内核及分析 第八周 进程的切换和系统的一般执行过程
学习笔记: 一.进程调度与进程调度的时机分析 1.不同类型的进程有不同需求的调度需求: 第一种分类: —I/O-bound:频繁的进行I/O,通常会花费很多时间等待I/O操作的完成 —CPU-boun ...
- Linux内核及分析 第七周 可执行程序的装载
实验步骤 1. 更新menu,用test.c覆盖test_exec.c 2. 把init 和 hello 放到了rootfs.img目录下,执行exec命令的时候自动加载了hello程序 3. 执行e ...
- Linux内核及分析 第五周 扒开系统调用的三层皮(下)
实验内容: 1.执行rm menu -rf命令,强制删除原有的menu 2.使用git命令 git clone https://github.com/mengning/menu.git 克隆新的men ...
- Linux内核及分析 第三周 Linux内核的启动过程
实验过程: 打开shell终端,执行以下命令: cd LinuxKernel/ qemu -kernel linux-3.18.6/arch/x86/boot/bzImage-initrd rootf ...
- Linux内核读书笔记第六周
主要内容: 什么是调度 调度实现原理 Linux上调度实现的方法 调度相关的系统调用 什么是调度 现在的操作系统都是多任务的,为了能让更多的任务能同时在系统上更好的运行,需要一个管理程序来管理计算机上 ...
- LINUX内核分析第六周学习总结——进程的描述与创建
LINUX内核分析第六周学习总结--进程的描述与创建 标签(空格分隔): 20135321余佳源 余佳源 原创作品转载请注明出处 <Linux内核分析>MOOC课程 http://mooc ...
- linux内核分析第六周学习笔记
LINUX内核分析第六周学习总结 标签(空格分隔): 20135328陈都 陈都 原创作品转载请注明出处 <Linux内核分析>MOOC课程 http://mooc.study.163.c ...
- LINUX内核分析第六周学习总结——进程的描述和进程的创建
LINUX内核分析第六周学习总结——进程的描述和进程的创建 张忻(原创作品转载请注明出处) <Linux内核分析>MOOC课程http://mooc.study.163.com/cours ...
随机推荐
- html中如何移除video下载按钮
我发现部分安卓手机使用video标签播放视频的时候会自带一个下载按钮,一般产品大多都不需要这一功能,那如何屏蔽下载按钮呢?有下面两种,请一定使用第一种方式,使用css控制会有兼容性问题,建议不要使用这 ...
- IAR新建MSP430工程
一.在IAR官网下载IAR for MSP430 软件 https://www.iar.com/iar-embedded-workbench/#!?architecture= 选择MSP430,然后 ...
- 网易云易盾CTO朱浩齐:我们是如何用AI赋能内容安全?
本文由 网易云发布. 5月19日,LiveVideoStack携手网易云易盾,共同打造了“娱乐多媒体开发应用实践”专题,帮助开发者和泛娱乐平台运营人员,提升技术能力,突破难点,拓展思路与视野. 在专 ...
- LintCode 896. Prime Product 简明题解
Given a non-repeating prime array arr, and each prime number is used at most once, find all the prod ...
- 计算机专业C语言编程学习重点:指针化难为易
C语言是面向过程的,而C++是面向对象的 C和C++的区别: C是一个结构化语言,它的重点在于算法和数据结构.C程序的设计首要考虑的是如何通过一个过程,对输入(或环境条件)进行运算处理得到输出(或实现 ...
- Linux入门第二天——基本命令入门(中)
一.文件搜索命令 1.文件搜索命令:locate 速度很快(具体见Linux工具网址的对比),注意无法找到新建的文件(原理暂不展开) locate命令其实是“find -name”的另一种写法,但是要 ...
- 20155308 2016-2017-2 《Java程序设计》实验3
20155308 2016-2017-2 <Java程序设计>实验3 实验内容 XP基础 XP核心实践 相关工具 实验步骤 (一)敏捷开发与XP 敏捷开发是一种以人为核心.迭代.循序渐进的 ...
- C语言复习20170821
函数 函数头部参数表里的变量称为形参,也是内部变量,只能在函数体内访问. 形参的作用是实现主调函数与被调函数之间的联系,通常将函数所处理的数据,影响函数功能的因素或者函数处理的结果作为形参.没有形参的 ...
- Oracle下如何用rman备份到特定的sequence
本文为摘抄,目的为方便日后阅读: http://docs.oracle.com/cd/B12037_01/server.101/b10734/rcmbackp.htm To determine the ...
- 【转载】C/C++杂记:深入虚表结构
原文:C/C++杂记:深入虚表结构 1. 虚表与“虚函数表” 在“C/C++杂记:虚函数的实现的基本原理”一文中曾提到“虚函数表”的概念,只是为了便于理解,事实是:虚函数表并不真的独立存在,它只是虚表 ...