练习

练习1:分配并初始化一个进程控制块

alloc_proc 函数(位于 kern/process/proc.c 中)负责分配并返回一个新的struct proc_struct结构,用于存储新建立的内核线程的管理信息。ucore 需要对这个结构进行最基本的初始化,你需要完成这个初始化过程。

alloc_proc函数的实现中,需要初始化的 proc_struct 结构中的成员变量至少包括:state/pid/runs/kstack/need_resched/parent/mm/context/tf/cr3/flags/name。

请在实验报告中简要说明你的设计实现过程。并回答如下问题:

  • 请说明 proc_structstruct context contextstruct trapframe *tf成员变量含义和在本实验中的作用是啥?(提示:通过看代码和编程调试可以判断出来)

练习2:为新创建的内核线程分配资源

创建一个内核线程需要分配和设置好很多资源。kernel_thread 函数通过调用do_fork函数完成具体内核线程的创建工作。do_kernel 函数会调用 alloc_proc 函数来分配并初始化一个进程控制块,但 alloc_proc只是找到了一小块内存用以记录进程的必要信息,并没有实际分配这些资源。ucore 一般通过 do_fork实际创建新的内核线程。do_fork 的作用是,创建当前内核线程的一个副本,它们的执行上下文、代码、数据都一样,但是存储位置不同。在这个过程中,需要给新内核线程分配资源,并且复制原进程的状态。你需要完成在 kern/process/proc.c中的 do_fork函数中的处理过程。它的大致执行步骤包括:

  • 调用alloc_proc,首先获得一块用户信息块。

  • 为进程分配一个内核栈。

  • 复制原进程的内存管理信息到新进程(但内核线程不必做此事)

  • 复制原进程上下文到新进程

  • 将新进程添加到进程列表

  • 唤醒新进程

  • 返回新进程号

请在实验报告中简要说明你的设计实现过程。请回答如下问题:

  • 请说明 ucore 是否做到给每个新 fork 的线程一个唯一的 id?请说明你的分析和理由。

练习3:理解proc_run函数和调用的函数如何完成进程切换的

请在实验报告中简要说明你对 proc_run 函数的分析。并回答如下问题:

  • 在本实验的执行过程中,创建且运行了几个内核线程?

  • 语句local_intr_save(intr_flag);....local_intr_restore(intr_flag);在这里有何作用?请说明理由

最后更新于