lab6 也是虚拟内存的一种应用,主要实现fork时的写时复制copy-on-write功能。
问题
xv6中的fork()系统调用将所有父进程的用户空间内存复制到子进程中。如果父进程用户空间很大,复制可能需要很长时间。更糟糕的是,这种复制工作经常被浪费;例如,子进程中的fork()后跟exec()将导致子进程丢弃复制的内存,可能根本就没有使用复制来的很大一部分内存。另一方面,如果父类和子类都使用一个页面,而其中一方或双方都编写该页面,则确实需要一个副本。
解决方法
写时拷贝(COW) fork()的目标是推迟为子进程分配和复制物理内存页,直到实际需要复制时才进行分配和复制。
COW fork()仅为子进程创建一个分页表,用户内存的pte指向父进程的物理页。COW fork()将父级和子级的所有用户pte标记为不可写。当任何一个进程尝试写其中一个COW页面时,CPU将出现页面错误。内核页错误处理程序检测到这种情况,为出错进程分配一个物理内存页,将原始页复制到新页,并在出错进程中修改相关的PTE以引用新页,这一次PTE标记为可写。当页面错误处理程序返回时,用户进程就能够写入该页面了。
COW fork()使得释放用户内存的物理页变得更为麻烦。一个给定的物理页可能被多个进程的页表引用,并且只有当最后一个引用消失时才应该被释放。
Implement copy-on write
实现:
在kalloc.c中增加物理内存引用计数
<