一、从开机加电到执行 main 函数之前的过程
Linux 0.11 的代码是用 C 语言编写的,但是在操作系统启动时先执行的是三个由汇编语言写成的程序(bootsect, setup, head)。因为 C 语言编写的用户应用程序必须在操作系统的平台上执行,所以需要先加载操作系统。
加载操作系统的时候,计算机刚刚加电,只有 BIOS 程序在运行,而且此时计算机处在 16 位实模式状态,通过 BIOS 程序自身的代码形成的 16 位的中断向量表及相关的 16 位的中断服务程序,将操作系统在启动盘的第一个扇区(512字节)的代码加载到内存,BIOS 能主动操作的内容也就到此为止了。对于第一扇区代码的加载,不论是什么操作系统都是一样的;从第二扇区开始,就要由第一扇区中的代码来完成后续的代码加载工作。
- 第一扇区:第一部分内核代码,引导程序,bootsect.s
- 规划内存
- 载入 setup.s
- 载入系统模块 system 模块(屏幕显示:Loading System…)
- 确定根文件系统
- 4 个扇区:第二部分内核代码,setup.s
- 提取内核运行所需的机器系统数据
- 破旧立新:废除 BIOS 中断,将 system.s 移动到内存地址起始位置
- 为保护模式做准备
- 240 个扇区:第三部分内核代码,system 模块
- 执行 head.s
- 创建内核分页机制,是内核能够掌控用户进程的基础之一
- 执行 head.s
加载工作完成后,并没有立即执行 main 函数。开机时的 16 位实模式与 main 函数执行需要的 32 位保护模式之间有很大的差距,head.s 来弥补这个差距。此时中断仍处于关闭状态。
二、设备环境初始化及激活进程 0
硬件初始化:
- 与主机有关的硬件初始化:规划内存格局,设置及初始化缓冲区,设置及初始化虚拟盘,初始化 mem_map,初始化缓冲区管理结构。
- 与外设有关的硬件初始化:设置根设备,初始化软盘,初始化硬盘。
为内核及进程的正确运行所做的初始化:中断服务程序的挂接,初始化进程 0。
用模拟中断的方法将进程 0 的特权级由 0 翻转到 3,实现激活进程 0。(除了进程 0 外,所有进程都要由一个已有进程在 3 特权级下创建)
三、进程 1 的创建及执行
操作系统启动以来,内核第一次进行进程调度。
进程 1 第一次执行后,设置硬盘信息,格式化虚拟盘,加载根文件系统。
四、进程 2 的创建及执行
进程 1 创建进程 2,加载 shell 程序,创建 update 进程,重建 shell,实现系统怠速。
进程 0 和进程 1 的代码都是操作系统设计者直接写到内核代码中的,进程 2 则是从硬盘中加载的执行代码,而且 shell 进程是对操作系统非常重要的用户界面进程,所以涉及打开终端设备以及大量的文件操作。
五、文件操作
操作系统对文件的一切操作都可以分为两个方面:
- 对文件管理信息的操作:新建,打开,关闭,删除文件
- 对文件数据内容的操作:读文件,写文件,修改文件
操作文件管理信息就是建立或解除进程与文件的关系链条,进程可以沿着关系链条,依托缓冲区与硬盘进行数据交互。当关系链条解除后,进程则不再具备操作指定文件的能力。
如果文件管理信息被更改,则操作系统要将此更改落实在硬盘上,以免失去对文件数据内容的控制。而文件数据内容的更改需要先在缓冲区进行操作,再写入磁盘。
六、用户进程与内存管理
- 线性地址
- 分页机制
- 进程调度
七、缓冲区和多进程操作文件
多进程操作文件的核心是多进程对缓冲区的操作。缓冲区关联着用户进程,文件系统和内存。
八、进程间通信
进程间通信通过管道。
信 机制是一种模仿软件中断机制。
九、操作系统的设计指导思想
Hello World
运行 Hello World 程序,操作系统为程序运行做了哪些工作。
- 用户输入命令,shell 进程被唤醒,对命令进行解析。
- 用户敲击键盘后,以文件系统的操作方式将输入的信息记录在终端设备文件上(tty0)。(需要一整套文件系统)
- 敲击键盘后,产生键盘中断信 ,系统对通过搜索中断描述符表找到键盘中断处理程序,并执行该程序。(需要一整套中断服务体系)
- 中断服务程序开始执行后,唤醒 shell 进程,通过进程调度机制,由进程 0 切换到 shell 进程去执行。(需要一整套进程管理机制)
- shell 进程通过执行自己的程序从 tty0 终端设备文件上读取用户键入的指令信息,然后解析该指令,并进行相应的处理。
- 每个字符的敲击都会重复上述动作。
- shell 程序解析出用户命令后,调用 fork 函数创建一个用户进程,以便对 Hello World 文件的程序进程控制。
- 进程结构包括:时间片,优先级,进程状态,进程对应的文件,进程的任务状态描述符(TSS)和进程的局部数据描述符表(LDT)。
- 进程的任务状态描述符(TSS):当前进程运行时所有寄存器中的数据。
- 进程的局部数据描述符表(LDT):当前进程的代码段描述符和数据段描述符。
- 新进程创建完毕后,加载 Hello World 文件对应的程序。
- 文件加载前检测可执行文件是否可用。
- 若具备载入文件的条件,则将文件载入内存。(页写保护和缺页中断)
- 程序执行,显示 Hello World。
操作系统的设计指导思想:主奴机制
在特权机制下,操作系统和应用程序为主奴关系。
通过进程的 task_struct 结构来划分程序的边界,创建进程就是创建 task_struct,所以进程 0 只能由操作系统创建,而可以由进程 0 复制创建子进程。
主奴机制的体现
- 进程调度:操作系统掌握进程调度的权利。
- 内存管理:用户进程不能越界访问,且使用逻辑地址空间。内核可以访问所有内存地址,并使用实际物理地址。
- 文件系统:用户进程的文件操作需要向内核提申请。
主奴机制的关键技术
- 保护和分页:用户进程的逻辑地址要由内核转换为线性地址。物理地址是由内核将线性地址转换而成的。用户进程需要使用内存时,先由内核将逻辑地址转化为一个线性地址,再根据内核提供的专门为进程设计的分页方案,由 MMU 转化为实际物理地址。
- 特权级:内核特权级可以在任何条件下执行所有的指令,而用户进程则不能。
- 中断:程序运行中,用户特权级和内核特权级的代码频繁交换,是因为有特权级的转换,其主要的方法就是中断。由于中断的发生不可预见,不可能由程序员处理,所以需要由操作系统来完成。普通的 call 似乎是沿着内存地址平滑移动到调用位置,而中断则似乎是脱离了内存,通过 CPU 硬件翻到内存中另一处中断服务程序的位置。
主奴机制的建立:先机
为什么内核程序能获得高优先级,而用户程序就不能p>
计算机开机启动的时候是实模式,没有特权级的概念。当操作系统的启动程序打开保护模式的时候,特权级状态必须是最高级。
一些恶意程序可以将代码驻留到系统引导区,甚至 BIOS,抢占先机来获取最高特权级。
硬件和软件的关系
软件就是进程,硬件就是文件。
进程
非用户进程:进程 0,进程 1,shell 进程。
- 进程 0 为在主机中有运行能力的进程。
- 进程 1 为有使用外设(文件)能力的进程。
- shell 进程为使用特殊外设的进程。
文件
- 内存,硬盘,缓冲区。
- 缓冲区要求多进程读写数据的正确性和尽可能高的效率。(数据的读写有序;数据在缓冲区中停留的时间尽可能长)
- 进程间通信使用的管道也是一个管理在内存中的虚拟文件。
父子进程共享页面
在子进程加载自身的代码之前,共享父进程的代码,等到加载自己的代码之后,在切断共享父进程代码的关系。否则没有加载自己代码的代码,就无法完成加载代码的工作。
为避免父子进程写数据冲突,有页写保护机制,防止多进程访问共享数据导致的数据混乱。
操作系统的全局中断与进程的局部中断:信
- 中断技术使操作系统由主动轮询变为被动响应,极大地降低了 IO 过程中主机资源的消耗,提高了运行效率。
- 信 技术模仿中断的技术路线,使进程间的沟通由主动轮询变为被动响应,大幅减少了进程间沟通引起的操作系统消耗,提高了整体运行效率。
- 区别:中断是针对操作系统的全局中断;信 是针对进程的局部中断。
文章知识点与官方知识档案匹配,可进一步学习相关知识CS入门技能树Linux入门初识Linux24975 人正在系统学习中
声明:本站部分文章及图片源自用户投稿,如本站任何资料有侵权请您尽早请联系jinwei@zod.com.cn进行处理,非常感谢!