0%

Prologue

这样的总结应该从何开始?我是从Bilibili刷视频偶然了解到与训练营相关的信息的。使用Rust语言编写操作系统的实践,我太喜欢这个方向了。因为我正学过一点Rust,也经学校老师的推荐看过CSAPP并完成了大多数的实验。其中我最喜欢的便是shlabattacklab────写一个shell!实在是有趣不过,如果再写一个操作系统呢?好吧,我应该没有与之匹配的实力,不过开源操作系统训练营就这样给了我一个类似的机会。报名人数破千!全程免费!还有什么好说的呢,杀😡。

Stage 1

110道Rustling编程题,并没有耗费我太多功夫,更多的是重新熟悉一下语法。我觉得,学习Rust不仅是学会如何使用一门编程语言,更是了解更多的编程范式。例如trait背后的组合大于继承;函数式编程对现代编程语言深刻的影响:默认不可变、闭包、HOFs、链式操作等;所有权与生命周期机制,这种RAII思想是C++首创的(但是opt-out)。Rust编译器就是你最好的老师,更别说还有满地走的各式AI(本总结经AI辅助完成),2025年的今天,学习Rust不应该再是一件难事🥳。

Stage 2

到了OS设计实现,主要是完成5道rCore操作系统大实验编程题。我是提前进入该阶段,所以全程并没有看过相关学习视频,而是跟随rCore-Tutorial-Guide文档完成的🤓。

这阶段最耗时的是lab2───地址空间和lab5───并发,这两个不管哪个太痛苦了😭。lab2是因为分页机制本身就相对复杂,层层抽象,读内核新增的代码就花了我很久时间(光论这一点文件系统其实不遑多让,不过到这里我的读代码能力已经得到显著锻炼了,所以带给我的痛苦远不及地址空间🥱)。而lab5,单纯是我因为技术路线的左右互博而无限拖缓了进度,我一直在对死锁检测资源的获取上究竟是现场构建还是跟随进程保存之间反复横跳。倒不如说,是因为我在实现这两个的时候遭遇多方掣肘,导致我不停怀疑我自己,不停的重构。使用Rust编程不就是戴着脚镣在跳舞吗?我现在水平还不够,只能写出不够优美的实现,但是我不会放弃的😡。

Stage 3

组件化操作系统,这大概是最各显神通的阶段了。我对这阶段的印象其实是一点草台味🤯,遇到各方面奇怪的问题,测试脚本死活不通过,各种不同的资料,到底要实现在哪里,我要怎么修改一个crate依赖的代码?我是个不撞南墙不愿意问别人的人,所以我全部都闭门造车自己解决了所有问题(真的吗?至少测例说我通过了)。但实际上,在讨论群里大家都很乐意回答别人的提问,每个人都有自己的“奇技淫巧”,应该让大家全都热烈讨论遇到的问题,才能让训练营变得更好😈。

Conclusion

写到这里我已经有点精疲力竭。我在参与前三个阶段的过程中收获颇多,不只是对整个组件化操作系统的认识。还有各种在学习过程中对工具的使用,helixZellij,这些工具,我很早就下载了,只是因为它是Rust重写的老工具。现在呢?我需要helix丰富的快捷键,我需要Zellij的分屏。我开始熟悉,正是我开始迈出一步,参加了这次,2025 春夏季开源操作系统训练营

完成了三阶段的任务,我也疲惫了,进入了一种拖延的状态。五月二十二号,新建文件夹,想要完成这篇总结报告。一直到今天,我终于又想重新出发了。希望到了第四阶段,我可以找到新的方向。

编程的乐趣:⭐️⭐️⭐️⭐️
挑战的难度:⭐️⭐️⭐️
开源训练营:⭐️⭐️⭐️⭐️⭐️

这次的学习rcore有点艰辛,因为是把一个操作系统内核给完成了,虽然也只是补充了syscall里面的函数,但是>把整体内核需要什么部件给摸索清楚了
出了有关rust语言特殊机制的bug,就看看别的函数是怎么写出规范的rust代码的,虽然看了文档后有个思路去写
那个函数,但是不知道怎么写时,参考周围代码就好多了,让我印象比较深的是,当一个结构体的对象要被调用>的时候,比如inner,通常需要加个exclusive_access()或者unwrap()等等,这个rust语言虽然没有像C语言>那么底层,但是感觉这么一写,就不会出现内存问题,很规范。再不会通常只能问大佬了哈哈哈。
在这个训练营,大佬云集,接触到了很多才学渊博的人,大家也来自不同的专业,有着不同的志向,也坚定了我>跨越专业去学习更多知识的信心。


title: 梦醒的学习记录
date: 2025-03-25 21:02:12
tags:
mathjax: true


今天重写了一遍rustlings,虽然在其他训练营已经写过了,但是这次依然有收获。比如我了解到了
match时的ref有什么作用,以及他和&的区别

2024三阶段总结

Unikernel

  • print_with_color

简单的利用ascll字符实现颜色

  • support_hashmap

看群内大佬讨论,就引了一个库

  • alt_alloc

这个难度不大,因为测例很简单。严格实现后我确实也不知道自己实现的正确与否

  • shell

原shell实现了有关rename的,rename我就直接调库了,然后通过创建文件、copy文件内容、删除原文件拼接除了mv的功能

  • 1115挑战(内存调度算法实现优化)

说来惭愧,我这个印象最深。我写了3次,第一次好像是80多,第二次直接没跑起来,第三次是链表指针不知道指到哪里去了….反正都没超过170,也就没提交….

宏内核

  • page_fault

难度适中? 感觉就是rcore上了一点

  • sys_map

就find_free_area然后read进去,虽然感觉用find_free_area找到的地方有些不符合man mmap的说明。

Hypervisor

第一次了解hypervisor具体是怎么操作、干了什么….涨知识了…

  • simple_hv

改一下guest的sepc,设置一下a0、a1的值

  • pflash设备模拟方式

一开始没有搞清gpa映射到hpa时,没有经过host的satp,导致在host中拿着pa当va来用,出现了问题。另外,在完成后,修改了一下pflash的内容,想要读u128转string输出,但是没想到,在对* u128解引用时,它居然会先读u128的高64位,导致映射时页面没对齐。

2024四阶段总结 - Starry-Next 项目二方向一 感想

仓库链接: https://github.com/yjymosheng/Starry-On-ArceOS/tree/main

最终 commit ID: 71650c57f8ef9a64a6bdf274d9890b5c0c96642d

目前进展:

已经完成的syscall

a

没有完成的syscall

b

个人感想 :

这时我第二次参加os训练营,第一次的时候连rcore都没有完成,这一次由于对syscall的理解不够,相比其他同学浪费了很多时间在img的调试上.

可能下一次就能拿到优秀学员证书了也说不定?一次更比一次强嘛

虽然我的四阶段的学习可能差强人意,但是对我来说算是打开了操作系统的大门,希望明年的操作系统大赛上,能够有新的突破.

通过这次训练营,我进行了第一次对操作系统的尝试,与还对系统调用有了更加全面的认识。编写一个自己的操作系统不再只是纸上谈兵,而是一种有希望实现的技术。回顾整个过程,既有苦涩,也有喜悦,更重要的是,这让我对操作系统这条路充满了信心和期待。

希望未来,我能够在操作系统道路上走得更远,探索更多未知的可能性!

荣誉准则

  1. 在完成本次实验的过程(含此前学习的过程)中,我曾分别与 以下各位 就(与本次实验相关的)以下方面做过交流,还在代码中对应的位置以注释形式记录了具体的交流对象及内容:

  2. 此外,我也参考了 以下资料 ,还在代码中对应的位置以注释形式记录了具体的参考来源及内容:

    我的参考资料:rCore-Tutorial-Book-v3

  3. 我独立完成了本次实验除以上方面之外的所有工作,包括代码与文档。 我清楚地知道,从以上方面获得的信息在一定程度上降低了实验难度,可能会影响起评分。

  4. 我从未使用过他人的代码,不管是原封不动地复制,还是经过了某些等价转换。 我未曾也不会向他人(含此后各届同学)复制或公开我的实验代码,我有义务妥善保管好它们。 我提交至本实验的评测系统的代码,均无意于破坏或妨碍任何计算机系统的正常运转。 我清楚地知道,以上情况均为本课程纪律所禁止,若违反,对应的实验成绩将按“-100”分计。

实验总结

文件系统章节是我花时间最多的一个章节,时间主要花在了对文件系统的理解上,看源码也费了些时间。将细节通过在线文档整理如下图所示:
ch6 基础知识

问答作业

Root Inode 的作用:
文件系统的入口点:在类 Unix 文件系统中,root inode 是文件系统层次结构的根,即 / 目录。它是访问文件系统其余部分的起始点。
存储目录信息:root inode 存储了根目录下的文件和子目录的元数据,例如它们的名称、inode 编号、文件类型(文件或目录)等。
维护文件系统结构:root inode 作为文件系统结构的起点,确保了整个文件系统的组织性和可访问性。
权限控制:root inode 还包含了访问权限信息,用于控制对根目录及其下内容的访问。
如果 Root Inode 损坏:
如果 root inode 中的内容损坏,可能会发生以下情况:

无法访问文件系统:由于 root inode 是访问文件系统的入口,如果它损坏,可能会导致整个文件系统无法挂载,用户无法访问任何文件或目录。
数据丢失:虽然文件数据可能仍然存储在磁盘上,但如果 root inode 损坏,系统可能无法定位这些数据,导致数据看似丢失。
文件系统损坏:文件系统的元数据完整性对于文件系统的健康至关重要。root inode 损坏可能导致文件系统元数据不一致,进而导致整个文件系统损坏。
恢复困难:恢复损坏的 root inode 可能非常困难,可能需要专业的数据恢复工具和专业知识。

荣誉准则

  1. 在完成本次实验的过程(含此前学习的过程)中,我曾分别与 以下各位 就(与本次实验相关的)以下方面做过交流,还在代码中对应的位置以注释形式记录了具体的交流对象及内容:

  2. 此外,我也参考了 以下资料 ,还在代码中对应的位置以注释形式记录了具体的参考来源及内容:

    我的参考资料:rCore-Tutorial-Book-v3

  3. 我独立完成了本次实验除以上方面之外的所有工作,包括代码与文档。 我清楚地知道,从以上方面获得的信息在一定程度上降低了实验难度,可能会影响起评分。

  4. 我从未使用过他人的代码,不管是原封不动地复制,还是经过了某些等价转换。 我未曾也不会向他人(含此后各届同学)复制或公开我的实验代码,我有义务妥善保管好它们。 我提交至本实验的评测系统的代码,均无意于破坏或妨碍任何计算机系统的正常运转。 我清楚地知道,以上情况均为本课程纪律所禁止,若违反,对应的实验成绩将按“-100”分计。

总结

地址空间映射这一章知识密度较高,反复看了几遍才基本弄懂,调试代码陆陆续续调试了3天。(还是太菜,菜就多练!)
简单总结下本章:在开启分页SV39分页之前,OS和都是直接访问物理地址,这给系统带来很多潜在的安全隐患,例如地址空间未隔离等。开启分页模式后,OS和用户代码中就都是虚拟地址了,需要通过页表和MMU进行转换,并且页表上的属性区分出了U和S,进行了权限和空间的隔离,分别在特权级和地址空间上保证了OS内核的安全,同时也保证了用户程序之间相互隔离,彼此空间不会重叠。(虚拟空间可以重叠,但通过页表映射后通常是隔离的,有种特殊情况是通过映射到相同的物理也实现内存共享)

另外为了OS在开启分页后能平滑的访问,对于OS采用的是恒等映射(虚拟页号=物理页帧)。而对于用户程序通常采用Framed映射,通过栈式页帧分配器分配页帧并和虚拟页号建立映射关系,动态生成页表及页表项,实现物理页帧的按需分配。

另外一个比较好的抽象是地址空间MemorySet,它作为任务的一部分,管理着页表及和逻辑区。在实现采用了RAIL机制,加上rust的所有权及drop trait自动实现页表项的释放。

笔记

第一题

最低的位则是标志位,它们的含义如下:
仅当 V(Valid) 位为 1 时,页表项才是合法的;
R/W/X 分别控制索引到这个页表项的对应虚拟页面是否允许读/写/取指;
U 控制索引到这个页表项的对应虚拟页面是否在 CPU 处于 U 特权级的情况下是否被允许访问;
G 全局页表项。这意味着即使是在上下文切换(例如,进程切换)之后,该页表项也不会被冲洗(flushed)或失效。简而言之,G位用于指示页表项在地址空间的多个上下文中保持有效。
A(Accessed) 记录自从页表项上的这一位被清零之后,页表项的对应虚拟页面是否被访问过;
D(Dirty) 则记录自从页表项上的这一位被清零之后,页表项的对应虚拟页表是否被修改过。

第二题

荣誉准则

  1. 在完成本次实验的过程(含此前学习的过程)中,我曾分别与 以下各位 就(与本次实验相关的)以下方面做过交流,还在代码中对应的位置以注释形式记录了具体的交流对象及内容:

  2. 此外,我也参考了 以下资料 ,还在代码中对应的位置以注释形式记录了具体的参考来源及内容:

    我的参考资料:rCore-Tutorial-Book-v3

  3. 我独立完成了本次实验除以上方面之外的所有工作,包括代码与文档。 我清楚地知道,从以上方面获得的信息在一定程度上降低了实验难度,可能会影响起评分。

  4. 我从未使用过他人的代码,不管是原封不动地复制,还是经过了某些等价转换。 我未曾也不会向他人(含此后各届同学)复制或公开我的实验代码,我有义务妥善保管好它们。 我提交至本实验的评测系统的代码,均无意于破坏或妨碍任何计算机系统的正常运转。 我清楚地知道,以上情况均为本课程纪律所禁止,若违反,对应的实验成绩将按“-100”分计。

实验总结

问答作业

荣誉准则

  1. 在完成本次实验的过程(含此前学习的过程)中,我曾分别与 以下各位 就(与本次实验相关的)以下方面做过交流,还在代码中对应的位置以注释形式记录了具体的交流对象及内容:

  2. 此外,我也参考了 以下资料 ,还在代码中对应的位置以注释形式记录了具体的参考来源及内容:

    我的参考资料:
    rCore-Tutorial-Book-v3
    https://zh.wikipedia.org/wiki/%E9%93%B6%E8%A1%8C%E5%AE%B6%E7%AE%97%E6%B3%95

  1. 我独立完成了本次实验除以上方面之外的所有工作,包括代码与文档。 我清楚地知道,从以上方面获得的信息在一定程度上降低了实验难度,可能会影响起评分。

  2. 我从未使用过他人的代码,不管是原封不动地复制,还是经过了某些等价转换。 我未曾也不会向他人(含此后各届同学)复制或公开我的实验代码,我有义务妥善保管好它们。 我提交至本实验的评测系统的代码,均无意于破坏或妨碍任何计算机系统的正常运转。 我清楚地知道,以上情况均为本课程纪律所禁止,若违反,对应的实验成绩将按“-100”分计。

总结

一直以来对OS非常感兴趣,通过本次的“代码调试”,熟悉了整个项目架构,并对OS有了进一步的深刻认识。在调试过程中不仅熟悉了OS,还对Rust语言有了更深入的认识。
本次实现的功能是打印任务信息:系统调用及调用次数,运行时间。
整体思路:在syscall入口处调用set_task_info方法。每调用一次系统调用,更新一次syscall_times和time。
踩的坑:需要注意Rust结构体与C结构体的区别,Rust编译器会对Rust中的字段进行重排序,以达到优化存储的目的。在OS中的结构体和user中的结构体字段要保持一致,否则会蛋疼:(
另外附图一张,表示我曾用心学习:)

笔记

第一题

应用分别出现:

  • PageFault in application, bad addr = 0x0 bad instruction = 0x804003a4 , kernel killed it.
  • IllegalInstruction in application, kernel killed it.
    使用的sbi版本是:RustSBI version 0.3.0-alpha.2

第二题

1.刚进入__restore时,a0代表kernel stack pointer , restore的两种使用场景:a.trap 恢复 b.创建新任务

2.处理了sstatus sepc sscratch。sstatus用于指定返回的特权级(SPP字段);sepc用于指定返回后执行哪条指令;sscratch存储着用户栈地址,U态程序要执行必须正确找到U态的栈地址。

3.application不会使用x4;x2已经被交换到了sscratch代表着用户栈指针

4.sp指向user stack , sscratch 指向kernel stack

5.__restore总状态切换在csrw sstatus,t0这行指令,sstatus中的SPP字段记录了陷入前的特权级,csrw sstatus,t0执行后,恢复到用户特权级。最后的指令sret ,指令返回用户程序,原因是该指令会从sepc中读取指令地址,并赋予pc寄存器,而U态的栈等已恢复好,sret临门一脚,步入U世界。

6.指令之前sp -> user stack , sscratch -> kernel stack ;指令后sp -> kernel stack, sscratch -> user stack。指令进入内核运行。并且用sscratch保存着U态的栈地址,从内核态返回即可用sscratch恢复用户态栈指针。

  1. csrrw sp,sccratch, sp是程序从U态进入S态的关键指令,sp指向内核栈。

荣誉准则

  1. 在完成本次实验的过程(含此前学习的过程)中,我曾分别与 以下各位 就(与本次实验相关的)以下方面做过交流,还在代码中对应的位置以注释形式记录了具体的交流对象及内容:

  2. 此外,我也参考了 以下资料 ,还在代码中对应的位置以注释形式记录了具体的参考来源及内容:

    我的参考资料:rCore-Tutorial-Book-v3

  3. 我独立完成了本次实验除以上方面之外的所有工作,包括代码与文档。 我清楚地知道,从以上方面获得的信息在一定程度上降低了实验难度,可能会影响起评分。

  4. 我从未使用过他人的代码,不管是原封不动地复制,还是经过了某些等价转换。 我未曾也不会向他人(含此后各届同学)复制或公开我的实验代码,我有义务妥善保管好它们。 我提交至本实验的评测系统的代码,均无意于破坏或妨碍任何计算机系统的正常运转。 我清楚地知道,以上情况均为本课程纪律所禁止,若违反,对应的实验成绩将按“-100”分计。


title: dream第二阶段总结
date: 2024-05-31 20:00:41
categories:
- 2024春夏季开源操作系统训练营
tags:
- author:Eternal60f3
- repo:https://github.com/Eternal60f3/2024-rcore-repo


很感谢这次训练营的主办方。我这学期准备考研,然后就也想这弄一个项目。为复试增加点东西。

rcore让我熟悉了gdb以及git的使用。借助vscode的插件也很方便的利用git来比对前后差异来debug。

对于这几个实验。

再看完ch3的文档,当时以为自己理解了,等实际去看代码的时候,发现自己理解个屁。又回到ch2分支,捋清楚ch2的代码之后,才搞懂ch3的实现。

实验4非常nice本来一开始一直没搞懂,为什么要设置 DiskInode 和 Inode 两层抽象,而不是一层,但实际开始写的时候突然意识到,这是对于fs资源保证只有一个人使用的管理。对于涉及到了锁的编程,以前没太写过,debug弄了好久。

实验5在群里和佬们交流了才搞懂该怎么弄,debug了也弄了好久。好在最后做出来了。

可惜,阶段三之后可能没啥时间弄了,得抓数学了。未来说不定还会来参加啦,哈哈哈。多谢清华给了这么好的学习机会