0%

2023开源操作系统训练营第二阶段总结报告-Linyuqiz

开始阶段

有一年私有云平台开发经验的 Go 开发工程师,有些许的 Rust 基础, 没有 Rust 相关的项目,对操作系统相关的东西一知不解。

在群友的闲聊下发现有 “Linux 源码趣读” 的系列文章,趁空闲的时间过了一遍,对操作系统的整体结构有一定认识,群友说这个讲的蛮浅显的,但是感觉对我这种没有啥操作系统基础的还是有很大的帮助的。

学习感受

一章一章的剥开操作系统的面纱,硬件机制、操作系统理论整体联络起来,渐渐实现一个可用的操作系统。

就目前完成到 ch5 来讲,Guide 的 ch4、ch5 的这部分内容不怎么连贯,基础比较差的我就只能硬读了。听说 rCore-Tutorial V3 的内容更全一点,等后面也对照这学习一下每章节的内容。

学习总结

似乎任何事情都逃不过这句话:“会者不难, 难者不会”,真正的难其实是对未知的恐惧。目前算是完成了这次训练营的基本过线目标:完成前三个作业。现在回头来看,都无非是对操作系统概念的学习和理解,并把这些理解到的概念真正转化成工程代码的一个过程。例如实验中你本就拥有一个完整的模拟环境,运算设备、硬件机制、目前标准的系统调用接口参考、经典理论(SV39 分页机制)等等,需要用自己理解操作系统概念去把这些东西组合在一起,最终提供一个基于底层基础设备提供的机制,为上层用户提供一个可靠的、安全的运行环境。

未知的事物并不可怕,可怕的是你认为它是永远无法被理解的。

ch0

这一部分是构建实验环境:本质上就是安装 Rust 工具链和编译安装 Qemu 模拟器。在尝试使用 classroom 在线环境失败后,决定本地部署环境。据目前所了解到的虚拟环境模拟工具来看(需要一个 Ubuntu 的系统环境),有传统虚拟机软件(Parallel、VMWare 等)、MutilPass(Ubuntu 系统特供)以及更加流行的 Docker 容器模拟,由于对桌面环境不是强需便直接排除了,、MutilPass 和 Docker 自己都比较熟悉,因更倾向于 MutilPass 的使用方式,所以最开始拿 MutilPass 创建的 Ubuntu 虚拟机安装环境,通过 VSCode 的 ssh 插件直接远程虚拟机开始基础环境部署,运行第一个 “Hello World!”。

后续训练营的群友有推荐使用 Orbstack 这款软件,了解之下发现确实好用,随而更换到这个软件,它的优势:
1、共享宿主机内核:CPU 全部共享到虚拟机、内存几乎接近全部也是给到虚拟机,创建一个 Ubuntu 虚拟机只要十几秒。
2、提供 Docker 命令:可以替换掉 Docker, 又可以少装一个软件了。
3、提供单节点 K8s 集群:像 Docker 一样,更加轻量、启动快。
4、唯一缺点:目前只支持了 MacOS 系统(刚好是 Mac),可能是因为是使用 Swift 开发的,看后续是否会支持 Linux。

ch1

这一部分主要是一步一步的讲解了如何从零开始构建一个可以运行在 Qemu 上的 Rust 操作系统程序:Hello World!,接触到了一些基础概念:系统级标准输出、系统级异常处理、内存基本布局,这些在具体的代码转化后是如何展现的,以及操作系统的入口:entry.asm 文件。

简单来讲,系统加电后会固定去读区特定的位置,也就是操作系统入口文件里的这部分内容,从而就进入了我们编写的 Rust 操作系统程序的 rust_main 入口,当然固定读取的操作是硬件提供的。

ch2

这一部分实现一个最简单的批处理系统。电脑内存本质上就只一个线性的存储结构:这一部分将系统程序需要占用的部分之外的存储结构以固定的布局方式排列在内存上,通过一个程序一个程序的加载执行来达到一次运行可以完成多个任务的系统。这部分也涉及到了 SU 态相关的东西。

ch3

操作系统在一定程度来讲算是一个处于“死循环”的程序,因为各种“中断”操作将读写设备、CPU 计算、任务处理等灵活的控制起来。这部分主要利用了“时钟中断”和任务切换这两部分内容来完成了一个分时多任务系统,通过时钟控制 CPU 不被某个程序长时间占用,这也是最基本的任务调度实现。

这一章的作业是提供一个系统调用来获取当前执行任务的基本信息,不考虑其他影响因素:也就是记录任务的启动时间、各种系统调用的次数和状态,当前已经存在“任务”的存储模型 Task,在其中记录信息并在状态流转处记录即可。

ch4

这一章介绍了 SV39 多级页表机制理论,基于该理论实现了实验里的多级页表,物理地址、虚拟地址的基本定义和对应的基本操作,以及 MMU 机制和 sapt 的理论定义模型,包含了对多级页表的重要解释,同时也通过图介绍了整个内存中操作系统和用户程序的布局。

这一章的作业是在开启多级页表机制下,适配 ch3 的作业实现,并完成 内存分配 mmap、和内存释放 mummap 系统调用: 基本的思路就是如何在多级分页开启的时候从内存获取到对应数据结构的地址并赋值,有物理地址和虚拟地址间的转换、页表的访问权限设置相关的内容。

ch5

这一章基于多级页表机制对任务执行这块进行再次抽象,加入了任务编号、任务队列管理,主要是对任务抽象的部分是需要花些时间需要理解理解。

这一章的作业是老作业迁移适配外,在实现 spawm 和 priority 系统调用接口功能:最主要的还是在对分级页表比较熟悉的情况下,对已经实现的任务管理功能,如 exec、fork 等实现的理解后,spawn 其实就是创建一个新的 TaskControlBlock 并添加到任务队列,并绑定给当前 TaskControlBlock 的 child 下,但同时也别忘记了给这个新的 TaskControlBlock 绑定 parent。另一个 priority 就用户可以设置这个值来简单的控制下程序执行的顺序,来让某些程序优先执行。

后续计划

看时间情况继续学习后续的 ch6、ch7、ch8 的内容,完成整个训练营任务。