操作系统MIT 6.S081学习记录(三)lab3:page tables

339 阅读3分钟

携手创作,共同成长!这是我参与「掘金日新计划 · 8 月更文挑战」的第2天,点击查看活动详情

speed up system calls

加速原理

为实现系统调用加速,操作系统会在用户态和内核态之间通过一种只读方式共享数据,这种只读方式体现为页表,我们要做的是了解页表映射(mapping)的过程。

官方教程指定完成步骤

  • 在kernel/proc.c中修改proc_pagetable()文件,参照RISC-V privileged architecture manual 小册子和程序中类似代码,确定权限条件,并使用mappages()
  • 在allocproc()函数中分配内存
  • 在freeproc中释放内存

官方没有提到需要自己摸索的步骤

  • 在kernel/proc.h中的proc结构体中加入struct usyscall*,这里我将变量命名为usyspage。
  • 如果仅仅完成了以上几步,make clean会出现"panic: freewalk: leaf",需要解除映射。

所有程序修改到的地方

proc.h

image.png

proc.c

proc_pagetbale

image.png

allocproc()

image.png 注意:新加入的函数应紧跟上一个allocate之后,在empty user page table之前(别问我怎么知道的,我顺序反了,debug了半天)

freeproc()

image.png

proc_freepagetable()

image.png

运行结果

image.png

print a page table

粗读实验要求体会

  • 不要打印无效的PTE
  • 物理地址的数量可能和示例不同,条目数和虚拟地址的数量应该是相同的(我认为这个体现了所学概念)

需要完成的步骤(注:此处有更新)

在kernel/defs.h中添加vmprint原型,使exec.c能找到这个文件

image.png (笔者2023重做实验时注:其实这个原型应该加在加在vm.c,因为实际函数是写在那里的,不过写在exec.c也没问题,因为只要调用函数的地方引用了defs.h头文件,就能用上这个函数,只是会让其他开发者很困惑。笔者重做时已经修正了这一处代码习惯,这里保留着截图以作诫勉)

修改kernel/vm.c,在其中添加vmprint相关代码,具体可参考freewalk()的写法以及使用 %p

freewalk代码

(上一个环节的报错提示来源,递归调用自身,稍加修改可变成打印详细信息) image.png

vmprint() image.png

主体代码放helper_vmprint()

image.png

(更新)在kernel/exec.c的return argc前加入如下代码:

if(p->pid==1) vmprint(p->pagetable) image.png

运行结果

image.png

Detecting which pages have been accessed

实验步骤

在kernel/sysproc.c中完善sys_pgaccess()函数。

需要传入三个参数,这里依题意分别设为addr,len,bitmask。 image.png 代码具体内容参考其他函数中argaddr()和argint()的用法(lab2中也用到过) image.png

  1. 分别对addr,len,bitmask进行处理,下标也分别是0,1,2
  2. 对应hints4中的边界处理
  3. 核心代码,遍历页表,并调用一个辅助函数vm_pgaccess(后续会提到)
  4. copyout()对应hints第3点

编写vm_pgaccess(写在vm.c中)

vm.c中的walk()函数可以用作参考

walk()函数如下: image.png

vm_pgaccess()函数如下: image.png

在riscv.h中定义PTE_A

打开文件找到相应位置后,发现其他的定义是这样。 image.png 那这个PTE_A可以直接顺接定义为5吗?其实是不行的!

翻看教程提供的这个手册

image.png 会发现这里A对应的位置是6。 image.png

最后还得在defs.h中添加vm.c那里加入 我们自己加上去的 vm_pgaccess,让系统能找到它

image.png

实验结果

make qemu一下

image.png

最终结果

make grade之后是这样的: image.png

注意事项:

  • 记得自己加入time.txt 和 answers-pgtbl.txt两个文件(评测不看你文件内容,只是看有没有这两个文件
  • 如果遇到Test usertests卡住不动的情况,耐心等一等,最终会有的。
  • 如果你已经忍不住crtl-c把进程终止了,再make grade后提示gdb端口被占用之类的,按提示输入了那两个命令又不起作用(提示找不到相关进程),只需要重新连接一下当前做实验的设备就行了

结语

以上是我完成实验后照着官网要求回忆步骤并打开相应文件截图的,某些步骤可能会有遗漏。 最后也感谢你能看到这里!