XV6:ptable初始化

时间:2015-04-04 15:34:51

标签: c proc xv6

我正在谈论:

struct {
struct spinlock lock;
struct proc proc[NPROC];
} ptable;

位于proc.c文件中。

有人可以解释一下它的初始化位置吗? 因为,在proc.c中我从来没有看到某些东西(进程)被添加到它。

更确切地说,让我们说我正在查看调度程序代码:

void
scheduler(void)
{
 struct proc *p;
 for(;;){
 // Enable interrupts on this processor.
 sti();
 // Loop over process table looking for process to run.
 acquire(&ptable.lock);
 for(p = ptable.proc; p < &ptable.proc[NPROC]; p++){
  if(p−>state != RUNNABLE)
  continue;
  // Switch to chosen process. It is the process’s job
  // to release ptable.lock and then reacquire it
  // before jumping back to us.
  proc = p;
  switchuvm(p);
  p−>state = RUNNING;
  swtch(&cpu−>scheduler, proc−>context);
  switchkvm();
  // Process is done running for now.
  // It should have changed its p−>state before coming back.
  proc = 0;
  }
 release(&ptable.lock);
 }
}

在:

for(p = ptable.proc; p < &ptable.proc[NPROC]; p++){

你可以看到我们正在循环遍历ptable中的每个进程。我的问题是,他们是如何到达那里的? 谢谢!

4 个答案:

答案 0 :(得分:3)

初始化。

struct {
struct spinlock lock;
struct proc proc[NPROC];
} ptable;

上面的代码定义了一个struct(没有名称),并将ptable初始化为此类型的一个结构。 也许你对这种语法感到困惑:

struct ptable {
struct spinlock lock;
struct proc proc[NPROC];
};

这里我们只定义一个结构名称ptable,并且没有初始化。

答案 1 :(得分:2)

您将无法在xv6的代码中找到初始化。这就是原因。

C将proc的int和enum变量初始化为0.当实现ptable时,struct proc proc[NPROC];创建一个包含64个进程的数组,其字段由语言初始化为0。 0恰好是UNUSED枚举的值。

allocproc通过ptable.proc循环查找state = UNUSED,然后将找到的第一个初始化为所有需要的值。因此,无需显式初始化数组中的结构。

答案 2 :(得分:1)

struct {
    struct spinlock lock;
    struct proc proc[NPROC];
}ptable;

它被分配在堆栈上并自动初始化。这里的技巧是它以GCC方式编写,也称为匿名结构。

答案 3 :(得分:0)

作为全局变量的结构体 ptable 在 xv6 内核启动期间作为 bootmain() 调用的一部分加载到内存中。因为它是全局的,所以默认值被初始化。 现在来看看它们如何实际用于存储过程以及何时修改条目。

  • 第一个进程由 userinit() 创建,它选择一个未使用的条目并将其用于设置自己的 PCB。
  • 在内核制作了手工制作的 initproc 之后,第一次调用调度程序就会发生,这就是您在此处所指的内容。
  • 由于调度程序将选择一个 RUNNABLE 进程,而我们现在唯一拥有的是 initproc 本身,因此它是开始运行的进程。
  • 它调用 fork() 以生成一个 shell,该 shell 在每次调用时调用 allocproc() 从 ptable 获取另一个未使用的条目并将其分配给进程。

这是在 fork 期间填充 ptable 的方式,并帮助 xv6 记录活动进程。