操作系统实战 ############ .. raw:: html
目录 .. sidebar:: 目录 .. contents:: .. raw:: html
.. note:: 对于一个庞大的系统,最大的误区是陷入细节而不知全貌。 .. figure:: https://img.zhaoweiguo.com/knowledge/images/cores/oses/compiler1.jpeg HelloWorld 编译流程 手动控制以上这个编译流程,从而留下中间文件方便研究:: $ gcc HelloWorld.c -E -o HelloWorld.i 预处理:加入头文件,替换宏。 $ gcc HelloWorld.c -S -c -o HelloWorld.s 编译:包含预处理,将 C 程序转换成汇编程序。 $ gcc HelloWorld.c -c -o HelloWorld.o 汇编:包含预处理和编译,将汇编程序转换成可链接的二进制程序。 $ gcc HelloWorld.c -o HelloWorld 链接:包含以上所有操作,将可链接的二进制程序和其它别的库链接在一起,形成可执行的程序文件 1. 源文件生成预处理文件: gcc -E HelloWorld.c -o HelloWorld.i 2. 预处理文件生成编译文件: gcc -S HelloWorld.i -o HelloWorld.s 3. 编译文件生成汇编文件: gcc -c HelloWorld.s -o HelloWorld.o 4. 汇编文件生成可执行文件:gcc HelloWorld.o -o HelloWorld 整体设计 ======== 内核结构&设计 ------------- 硬件资源有:: 1. 总线,负责连接各种其它设备,是其它设备工作的基础。 2. CPU,即中央处理器,负责执行程序和处理数据运算。 3. 内存,负责储存运行时的代码和数据。 4. 硬盘,负责长久储存用户文件数据。 5. 网卡,负责计算机与计算机之间的通信。 6. 显卡,负责显示工作。 7. 各种 I/O 设备,如显示器,打印机,键盘,鼠标等。 软件资源有:: 计算机中的各种形式的数据。如各种文件、软件程序等 .. figure:: https://img.zhaoweiguo.com/knowledge/images/cores/oses/design1.jpeg 经典计算机结构图 内核作为硬件资源和软件资源的管理者,其内部组成在逻辑上大致如下:: 1. 管理 CPU,由于 CPU 是执行程序的,而内核把运行时的程序抽象成进程,所以又称为进程管理。 2. 管理内存,由于程序和数据都要占用内存,内存是非常宝贵的资源,所以内核要非常小心地分配、释放内存 3. 管理硬盘,而硬盘主要存放用户数据,而内核把用户数据抽象成文件,即管理文件,文件需要合理地组织,方便用户查找和读写,所以形成了文件系统。 4. 管理显卡,负责显示信息,而现在操作系统都是支持 GUI(图形用户接口)的,管理显卡自然而然地就成了内核中的图形系统。 5. 管理网卡,网卡主要完成网络通信,网络通信需要各种通信协议,最后在内核中就形成了网络协议栈,又称网络组件。 6. 管理各种 I/O 设备,我们经常把键盘、鼠标、打印机、显示器等统称为 I/O(输入输出)设备,在内核中抽象成 I/O 管理器。 除了这些必要组件之外,根据功能不同还有: a. 安全组件 b. 驱动程序 管理和控制各种硬件而编写的对应的代码 内核架构:: 1. 宏内核架构 2. 微内核架构 宏内核有极致的性能,微内核有极致的可移植性、可扩展性。 操作系统内核分为三个大层,分别是:: 1. 内核接口层 定义了一系列接口,主要有两点内容,如下: 这套接口的代码,就是检查其参数是否合法,如果参数有问题就返回相关的错误, 接着调用下层完成功能的核心代码。 2. 内核功能层 内核功能层的模块如下: a. 进程管理 b. 内存管理 c. 中断管理 d. 设备管理 3. 内核硬件层 主要包括一个具体硬件平台相关的代码,如下: a. 初始化,初始化代码是内核被加载到内存中最先需要运行的代码 例如初始化少量的设备、CPU、内存、中断的控制、内核用于管理的数据结构等 b. CPU 控制,提供 CPU 模式设定、开、关中断、读写 CPU 特定寄存器等功能的代码 c. 中断处理,保存中断时机器的上下文,调用中断回调函数,操作中断控制器等 d. 物理内存管理,提供分配、释放大块内存,内存空间映射,操作 MMU、Cache 等 e. 平台其它相关的功能,有些硬件平台上有些特殊的功能,需要额外处理一下 .. figure:: https://img.zhaoweiguo.com/knowledge/images/cores/oses/design2.jpeg 内核结构 .. figure:: https://img.zhaoweiguo.com/knowledge/images/cores/oses/linux1.png Linux 内部的全景图: https://makelinux.github.io/kernel/map/ .. figure:: https://img.zhaoweiguo.com/knowledge/images/cores/oses/linux2.jpeg Linux 五大重要组件 程序的基石:硬件 ================= CPU 的工作模式有:: 1. 实模式 实模式又称实地址模式,实,即真实,这个真实分为两个方面, 一个方面是运行真实的指令,对指令的动作不作区分,直接执行指令的真实功能, 另一方面是发往内存的地址是真实的,对任何地址不加限制地发往内存。 2. 保护模式 3. 长模式 .. figure:: https://img.zhaoweiguo.com/knowledge/images/cores/oses/register1.jpeg 实模式下的寄存器 .. figure:: https://img.zhaoweiguo.com/knowledge/images/cores/oses/register2.jpeg 保护模式下的寄存器 .. figure:: https://img.zhaoweiguo.com/knowledge/images/cores/oses/register3.jpeg 长模式下的寄存器 现代内存管理模式——分页模型:: 把虚拟地址空间和物理地址空间都分成同等大小的块,也称为页,按照虚拟页和物理页进行转换。 根据软件配置不同,这个页的大小可以设置为 4KB、2MB、4MB、1GB .. figure:: https://img.zhaoweiguo.com/knowledge/images/cores/oses/page1.webp 分页模型框架图:MMU工作原理图。一个虚拟页可以对应到一个物理页,由于页大小一经配置就是固定的,所以在地址关系转换表中,只要存放虚拟页地址对应的物理页地址就行了。 .. figure:: https://img.zhaoweiguo.com/knowledge/images/cores/oses/mmu1.webp MMU页表原理图 对于每个进程而言,它会误认为(被操作系统欺骗)自己独有所有地址空间,因此它访问地址是不会考虑任何问题的,可是这个地址是虚拟地址,待被MMU翻译后会得到对应的页表,而这个页表由操作系统管理,不同的进程拥有不同的页表,也因此产生了进程地址空间隔离,但是多个进程也是可以共享某个页表,这也是进程通信(IPC)的根本手段。 .. note:: CPU 大多数时间在执行相同的指令或者与此相邻的指令。这就是大名鼎鼎的程序 **局部性原理** 如何写出让 CPU 跑得更快的代码:: 1、遵从80-20法则,程序80%的时间在运行20%或更少的代码,针对热代码进行优化,才容易产出效果; 2、遵从数据访问的局部性法则,按数据存放顺序访问内存效率远高于乱序访问内存效率,也就是尽量帮助CPU做好数据Cache的预测工作。同样根据Cache大小,做好数据结构的优化工作,进行数据压缩或数据填充,也是提升Cache效率的好方式; 3、遵从指令访问的局部性法则,减少跳转指令,同样是尽量帮助CPU做好数据Cache的预测工作;现代CPU都有一些预测功能【如分支预测】,利用好CPU的这些功能,也会提升Cache命中率; 4、避免计算线程在多个核心之间漂移,避免缓存重复加载,可以绑定核心【物理核即可,不用到逻辑核】,提高效率; 5、去除伪共享缓存:在多核环境下,减少多个核心对同一区域内存的读写并发操作,减少内存失效的情况的发生; ===开始跑题=== 6、合理提高进程优先级,减少进程间切换,可以变相提供Cache提速的效果 7、关闭Swap,可以变相提供内存提速、Cache提速的效果; 8、使用Intel自家的编译器,开启性能优化,很多时候可以提速运算效率; 9、使用C语言,而不是更高级的语言,很多时候可以提速运算效率; 10、直接使用昂贵的寄存器作为变量,可以变相提供加速效果; 同步原语 ======== 使用信号量的步骤:: 第一步,获取信号量。 第二步,代码执行流开始执行相关操作,例如读取键盘缓冲区。 第三步,释放信号量。 锁是解决并发同步问题的关键,锁有两个核心点:: 一个是原子操作 通过原子操作来实现临界区标志位的改变, 一个则是中断 关闭中断来避免 CPU 中途离开导致数据同步失败问题 参考 ==== 1. 王爽老师的《汇编语言》: https://book.douban.com/subject/25726019/ 2. 李忠老师的《X86 汇编语言:从实模式到保护模式》 3. 《计算机组成与设计:软硬件接口》 4. 《UNIX 传奇:历史与回忆》(兴趣拓展向) 5. 李忠老師的《穿越計算機的迷霧》,學習一點硬件原理 * 王爽汇编的笔记 快速入门: https://blog.csdn.net/u013570834/article/details/108753839 * 视频: https://www.bilibili.com/video/BV1d4411v7u7