功能指针的任务调度

任务计划程序是使用函数指针的最常见应用程序之一。每个嵌入式系统都包含某种类型的任务调度程序,无论它是简单的循环循环还是最新的实时操作系统(RTOS)。使用功能指针进行任务调度的最简单方法之一是协作调度器。合作调度程序是一种美化的循环循环,具有监视系统时间并在特定时间间隔执行任务的能力。它会不间断地执行单个任务,直到完成为止,然后再继续执行下一个任务。换句话说,它不支持抢占,抢占将允许较高优先级的任务中断较低优先级的任务。协作排程器不允许为任务分配优先级。

调度程序要求每个任务必须具有三个基本参数才能起作用。任务间隔,上次执行时间和应执行的功能。任务间隔定义了任务应运行的频率。此间隔应在系统时间滴答中定义,并与由计时器以恒定速率递增的变量关联。在设计系统刻度时应小心谨慎,以确保自动更新更新的变量。通常为间隔最短的任务设置计时器。在大多数系统中,这取决于1或10毫秒的系统滴答声,具体取决于应用程序和所需的分辨率。 LastTick变量包含上一次执行任务的系统时间。这样做的目的是允许调度程序计算是否应该再次运行任务。最后,调度程序需要知道通过使用函数指针来执行哪个函数。

清单1

清单1– TaskType Definition

可以在一个名为TaskType的typedef结构中定义每个任务的需求。可以在代码清单1中找到TaskType的定义。在此示例中,函数指针是一个空指针,它不返回任何内容。由于TaskType结构定义了每个任务所需的所有信息,因此可以创建一个TaskType数组来存储所有系统任务。代码清单2显示了一个名为Tasks的数组的示例,其中包含系统中每个任务的定义。

Listing2

清单2–任务数组定义

关于Tasks数组要注意的重要一点之一是,它包含一个间隔为零的名为Tsk的任务。 Tsk是连续任务或空闲任务,调度程序在每次检查是否需要执行任务时都会执行Tsk。其余任务是定时任务,将在初始化间隔执行。掩码INTERVAL_XXXXMS是#define语句,包含在达到间隔之前必须发生的系统刻度数。请注意,“任务”中每个元素的LastTick索引都设置为零。这表明所有任务都在系统滴答0处运行,并且直到它们的时间间隔到期才第一次运行!例如,1000毫秒任务将在系统启动后的1000毫秒(不是在0毫秒和1000毫秒的时间)首次执行。如果由于某种原因开发人员希望在系统启动后将500毫秒任务的运行时间延迟一秒,则可以将LastTick从0更改为1000(假设系统刻度设置为1毫秒间隔)。最后,Tsk_XXms是按间隔执行的函数。通过以这种方式列出功能,功能的地址存储在功能指针中。关于以这种方式分配任务的一个有趣的观点是,要添加新任务,所有需要做的就是向表中添加新条目。

由于调度程序将被重用,因此需要一种在初始化期间获取配置表中的任务数以及调度程序的配置表地址的方法。代码清单3和4分别显示了如何定义执行此目的的功能。在系统初始化期间,将在main的开头调用此函数以初始化调度程序。

Listing3

清单3–Tsk_GetConfig函数

Listing4

清单4–Tsk_GetNumTasks函数

有了基础工作,调度程序要检查的下一个关键组件就是主循环。清单5中提供了整个主循环。Main通过定义一些调度程序变量开始。其中包括系统刻度变量,用于存储任务表位置的TaskType指针,用于在任务表中移动的TaskIndex变量,以及用于定义任务表中定义了多少个任务的NumTasks。在调度程序开始调度任务之前,它会通过Sys_Init函数初始化系统。

上市5

清单5– Scheduler Main Loop

调度程序的设置完成后,代码将进入无限while循环,该循环将连续运行调度程序代码。调度程序首先获取当前系统的滴答值。在示例代码中,假定这是原子操作(即在32位计算机上执行)。然后,调度程序使用设计用于检查任务表中每个条目的简单for循环。调度程序首先检查任务条目是否为连续任务。如果是,则执行任务的函数指针。如果任务不是连续任务,则将比较当前系统时间与上次执行任务之间的时间差,然后对照任务间隔进行检查。如果间隔已达到或超过间隔,则运行任务。为了执行任务,调度程序取消引用与任务关联的功能指针。然后,针对该任务更新表中的LastTick条目,然后检查下一个任务。

在任务计划程序中使用功能指针可大大简化计划程序的实现。如果不使用功能指针,任务调度器将变成难以管理的混乱代码,难以维护或重用。函数指针允许使用一个简单的表来包含所有任务,并使用for循环来检查每个任务并确定是否应执行该任务。这篇文章几乎没有涉及任务调度的内容,而是着重于函数指针的示例应用程序。

发表评论

您的电子邮件地址不会被公开。 必需的地方已做标记 *

该网站使用Akismet减少垃圾邮件。 了解如何处理您的评论数据.