调度器监视器

描述

描述复杂系统(如调度器)的监视器很容易变得庞大,以至于由于许多可能的状态转换而难以理解。通常可以将此类描述分解为更小的监视器,它们共享部分或所有事件。事实上,同时启用这些更小的监视器,就如同我们有一个单一的、更大的监视器来测试系统。将模型拆分为多个规范不仅更容易理解,而且在出现错误时能提供更多线索。

sched 监视器是一组用于描述调度器行为的规范。它包含多个独立的、按 CPU 和按任务的监视器,用于验证调度器应遵循的不同规范。

为了使该系统尽可能简单,sched 规范是 嵌套 监视器,而 sched 本身是一个 容器。从接口角度来看,sched 将其他监视器作为子目录包含进来,对 sched 启用/禁用或设置反应器会将更改传播到所有监视器,但单个监视器也可以独立使用。

重要的是,未来的模块在其容器(本例中为 sched)之后构建,否则链接器将不尊重顺序,并且嵌套将无法按预期工作。为此,只需将它们添加到 Makefile 中 sched 之后即可。

规范

sched 中包含的规范目前仍在进行中,它们改编自 Daniel Bristot 在 [1] 中定义的规范。

目前我们包含了以下内容:

监视器 tss

任务调度时切换 (tss) 监视器确保任务切换仅发生在调度上下文中,即在对 __schedule 的调用内部。

                   |
                   |
                   v
                 +-----------------+
                 |     thread      | <+
                 +-----------------+  |
                   |                  |
                   | schedule_entry   | schedule_exit
                   v                  |
  sched_switch                        |
+---------------                      |
|                       sched         |
+-------------->                     -+

监视器 sco

调度上下文操作 (sco) 监视器确保任务状态的更改仅发生在线程上下文中。

                      |
                      |
                      v
  sched_set_state   +------------------+
+------------------ |                  |
|                   |  thread_context  |
+-----------------> |                  | <+
                    +------------------+  |
                      |                   |
                      | schedule_entry    | schedule_exit
                      v                   |
                                          |
                     scheduling_context  -+

监视器 snroc

在其自身上下文中设置为不可运行 (snroc) 监视器确保任务状态的更改仅发生在相应任务的上下文中。这是一个按任务的监视器。

                      |
                      |
                      v
                    +------------------+
                    |  other_context   | <+
                    +------------------+  |
                      |                   |
                      | sched_switch_in   | sched_switch_out
                      v                   |
  sched_set_state                         |
+------------------                       |
|                       own_context       |
+----------------->                      -+

监视器 scpd

禁用抢占调用调度器 (scpd) 监视器确保在禁用抢占的情况下调用调度器。

                     |
                     |
                     v
                   +------------------+
                   |    cant_sched    | <+
                   +------------------+  |
                     |                   |
                     | preempt_disable   | preempt_enable
                     v                   |
  schedule_entry                         |
  schedule_exit                          |
+-----------------      can_sched        |
|                                        |
+---------------->                      -+

监视器 snep

调度器不启用抢占 (snep) 监视器确保调度器调用不会启用抢占。

                      |
                      |
                      v
  preempt_disable   +------------------------+
  preempt_enable    |                        |
+------------------ | non_scheduling_context |
|                   |                        |
+-----------------> |                        | <+
                    +------------------------+  |
                      |                         |
                      | schedule_entry          | schedule_exit
                      v                         |
                                                |
                        scheduling_contex      -+

监视器 sncid

未禁用中断调用调度器 (sncid) 监视器确保调度器未在禁用中断的情况下被调用。

                     |
                     |
                     v
  schedule_entry   +--------------+
  schedule_exit    |              |
+----------------- |  can_sched   |
|                  |              |
+----------------> |              | <+
                   +--------------+  |
                     |               |
                     | irq_disable   | irq_enable
                     v               |
                                     |
                      cant_sched    -+

参考资料

[1] - https://bristot.me/linux-task-model