#### 调度的来源

1. 发生计时器中断，进而执行`yield`函数
2. 进程使用了睡眠锁，等待设备或管道I/O的完成
3. 进程执行了`exit`系统调用
4. 进程使用`wait`系统调用等待子进程退出
5. 进程使用`sleep`和`wakeup`机制

#### 调度的过程

所有的PCB都放在顺序表`proc[]`里，顺序表`cpus[]`用以保存每个cpu的`scheduler()`的上下文。调度的过程就是`proc[]`里的进程与`cpus[]`里的调度器之间切换。

`swtch()`的作用是保存当前上下文，切换到目标上下文。

`scheduler()`是按值查找顺序表，调用`swtch()`切换到其它进程。

`sched()`是调用`swtch()`切换到`scheduler()`。

#### 睡眠与唤醒的原理

`sleep()`修改顺序表`proc[]`里当前进程所对应PCB的值，然后执行`sched()`切换到`scheduler()`。

`wakeup()`是按值查找`proc[]`，然后修改对应元素的值。

管道是使用`sleep()`和`wakeup()`的一个例子。