关键词:微控制器 实时多任务 指令
微控制器系统即国内通常所称的单片机系统,主要用于物理设备的接口和直接控制。虽然控制逻辑相对微处理机系统而言比较简单,但由于多数情况下需要实时响应,而且经常要同时处理多个对象的协同工作,因此,不仅对程序的运行效率有较高的要求,还要求微控制器具备较强的多任务处理能力。另一方面,由于量大面广,以及具体应用条件的限制,希望微控制器的成本要低;而这又只有在微控制器的硬件结构相对简单的前提下才能实现,这就限制了微控制器的指令、程序代码空间以及数据存储容量。在这样的局面中,想要实现较高的运行效率,就只有加强微控制器指令的功能和灵活性。
至今,绝大多数微控制器程序的编制仍使用汇编语言,其优缺点已众所周知。随着硬件技术的发展,器件的性能价格比显著提高,各种面向嵌入式应用的微控制器系统模块向商品化发展。微控制器系统的成本中,软件比例不断增加,使用高级语言编制微控制器应用系统的软件是必然的趋势;而且微控制器中能进行算术运行和逻辑运算的运算器结构、可以直接与数据总线交换数据并进行关系运算的单元个数、间址访问的能力等因素,将直接影响高级语言生成机器代码的难易程度。为完成某一运算,不能只计算运算本身所需的时间,还要考虑建立本处理环境所需的时间、取运算对象与保存运算结果的辅助操作时间、以及所占用的指令空间。简言之,要考虑所有影响6代码效率和运行效率的因素。
转移控制指令是直接影响程序运行的,但其前提是状态检测或者关系运算的结果;而状态检测需要位寻址能力的支持,关系运算又必须访问两个对象,所以,位寻址能力、数据访问能力、数据访问方式都与程序的运行效率有关。根据作者多年编制实时应用程序的体会,针对实时多任务应用,就高效率的微控制器数据访问能力、方式与转移控制指令设计而言,应具备以下四方面性能。
1.指令的关系运算能力
关系运算是控制程序转移的前提,其运算能力由两个方面组成:一是运算功能;二是运算单元数目。
在8位机系统中,运算功能一般都支持无符号的大于、小于、等于、不等于比较;在16位机系统中,还应支持有符号的比较,并且要求有多个运算单元都支持关系运算。如果常用的一些功能单元个数较少,则当进程切换时,要花费时间置换资源。假如微控制器中只有一个寄存器能进行关系运算,必须经常进行中间结果的换位存取。这些额外操作的代价是指令数目与运行时间的增加,那将极大地影响程序运行效率。例如,要根据两个关系运算的结果决定处理策略,首先,要将第一次关系运算的逻辑结果保存起来,可能还需要保留运算后的数据结果,再装入第二次需要的运算对象。其最小代价是多中用一条指令的存储空间和一次装入所需的运算时间,而且没有任何的额外收益。此外,多任务运行时将频繁产生中断,在中断服务程序中,必须腾出运算器,又要多占用一个堆栈空间来保存断中数据,以及一次进栈、一次出栈的两条指令的存储空间和运行时间。这些都是在微控制器应用系统中的宝贵资源,因此,这样的微控制器是不适应实时多任务系统应用的。现在,许多微控制器都采用寄存器组的结构,每一个寄存器都可支持关系运算和简单的算术运算功能,便于实现高级语言中“局部变量”的特性。其主要优点是存储器的利用率高,数据完全性好。这就大大缓解了运算能力的瓶颈。
2.指令的数据访问能力
(1)运算对象的访问方式
指令对运算对象的访问方式非常重要。如果同类资源只能使用特定名称区分访问。则处理多进程时,功能相似的程序段必须书写不同的代码段。代码重用性差,这就增加了总代码长度。所以,间址访问非常重要,它可以用同样的程序处理不同的对象,在多任务处理环境中能显著提高系统效益。
位信息是二进制中最基本的数据。控制系统中,经常需要检测位信息,例如进程的标识、外设的状态等。在多任务系统中,各进程将占用不同物理地址的系统资源。这时,指令能否支持间址的位访问,就大大影响进程之间的切换。如果不支持间址的位访问,假设有8位信息点,则必须编写8句直接位检测的语句来判别,增加了代码的长度;如果各进程要使用同一个代码段,必须为各进程置换重用的资源,浪费时间;而如果各进程使用不同的资源,则必须书写代码功能相同、仅仅资源不同的代码。现在常用的微控制器,位间接寻址能力都比较差,编写程序费时费力,代码冗长,修改困难。
对于字节数据,要求提供既可对数据代码区,又可对程序代码区的间址访问支持。当前常见的微控制器,虽然也提供对程序代码区的间址访问支持,但限于查表操作。应用程序要访问存放于数据内的常数,必须先调用查表程序获取对象,再将它放入某个工作单元,然后才能开始处理。如果能通过间址直接访问程序存储器中的数据表,则节省了时间与空间的开销。
(2)数据描述能力
随着人工智能、自适应、自学习技术的发展,参与关系运算的两个对象经常都是变量,微控制器指令系统的设计必须考虑这一因素。
关系运算的两个对象,应该支持运算器与立即数、寄存器、直接寻址或者间接寻址对象的关系运算;而间接寻址对象可以放在数据存储区中,也可以在程序存储区中。考虑到数组、队列的运算需要,比较理想的是间址寄存器支持指定次数循环或者支持循环队列操作。
相对寻址能力;采用一个基指针,再与间址寄存器叠加形成访问地址。既可访问程序代码空间。便于查表操作,用空间资源换取时间,提高非线性运算的处理速度;又可访问数据存储空间,便于计算机辅助开发应用程序生成运行代码中数据间址访问。
3.原子操作指令支持
同步与互斥是多进程必须处理的问题。多进程抢占系统资源时,要先判断系统资源使用标识。一般用一个位标识,是空闲则占用。这是一种互斥行为,一旦资源被占用,其它进程不得使用。为了避免一个进程检测到系统资源空闲之后,但在未改变标识位之间,另一个进程也检测到该资源空闲,必须将检测与改变标识设计为原子操作。一般,都通过禁止系统中断来解决。在检测之前关闭中断,检测之后再开启中断。如果指令提供对标志位以及对标识字节的原子操作支持,将减少程序并提高效率。
(1)标识位操作指令
要求对标识位的检测、清除标识位以及转移,在一条指令内完成。这在有些微控制器中已有指令支持。
(2)适应信号灯操作的指令
多进程并发运行时,经常用到信号灯技术。为了适应PV操作等同步与互斥操作,微控制器应提供减一等于某值转移,以及增一等于某值转移这样的指令支持。这样就可免去信号监测前后的关闭、开启中断操作,而仅在需要保护临界区时才关闭中断。禁止中断的时间减少了,相当于系统响应实时事件的能力增强。除了支持与常数的比较之外,指令还应支持与某寄存器或者间址存储单元的比较,这样就相当灵活。当该指令中的比较值取为0时,就是常用于控制循环的指令。
4.支持多进程切换的指令能力
当系统资源不能满足运行需要时,就要将进程挂起,同时也需要保留断点信息。从原理上讲,凡是进程自用的各种信息,都必须保留,进程下次由就绪态转为运行时,要以它们为依据,经过多次判断后才能恢复断点信息。可见,挂起过程和恢复过程要无谓地占用CPU时间。为解决这一矛盾,应设计如下指令功能。
(1)带回下次入口地址的调用返回指令
程序运行到某点,即隐含了条件的满足。进程挂起点的空间位置,隐含着进程运行的轨迹,即包含了挂起的原因。进程再次获得CPU资源,只要回到该点,再配以新状态条件,即可迅速恢复运行,而不需要重新再判别历史条件。因此,微处理器应该支持以指针间址存储单元内容(数据)为转移地址的调用指令,采用类似推栈指针重置PC指令的方法,用间址访问获取调用的入口地址。调用返回时,带回下次的入口地址,仍用该间址指针更新转移地址。
下次的入口地址,实际上并不需要放在哪个寄存器中带回,只要执行调用返回指令时,将当前程序计数器中的PC值(它已经含有下条指令首地址)送以用间址指针指向的存储单元即可,这种方法可以在8位机系统中方便地实现。它与常规的调用返回恢复调用点地址的做法不同之处在于先做了一步保存PC值的工作。调用返回指令有两种:其一是保存当前PC值并返回,下次调用直接转向指定入口;另一种则不保存当前PC值而返回,下次调用仍旧进入原入口。
为支持这种调用返回机制,在它之前的语句通常是一条判断转移指令,当不满足进程继续运行条件就执行调用返回。为提高指令效率,判断转移指令必须是双向的:有进程转移和无进位转移;零状态转移和非零状态转移;相等转移和不相等转移;大于转移和小于转移。对于位操作中的判断并清除标识位再转移的原子操作指令,则最好再提供判断并置位标识位再转移指令,以方便使用。
(2)支持可变中断矢量
实时系统普遍采用中断技术,许多微控制器采用固定中断矢量的实现方法。不同情况下的中断也只能执行相的指令段,而必须要在中断服务程序中辨别当前状况,一般,编程者都采用增设状态变量的方法,供下次中断服务时指引处理路径。本次中断结束之间的这部分准备工作以及下次进入中断时的寻找路径,都是无谓消耗CPU资源与时间;而采用可变中断矢量的实现方法,进入中断服务之后直接到达任务处理点,可避免上述弊端,提高中断服务响应速度。具体方法类似调用返回的处理,保存本次中断处理服务程序的终止点地址作为新的中断向量即可。
(3)组合条件对进程状态转移的控制
对于16位处理器,还可以提供以当前指令为基地址,以寄存器内容作为偏移地址的直接跳转或者调用支持。
进程需要处理多因素条件 综合与抉择,运行时要探测信息标识,依据多个状态变量决定运行路径。设有n个信息标识,由它可引导k(k≤2 n)条路径。采用逐个辨识的方法。需n次;而如果将这n个信息标识作为矢量地址看待,与基地址共同形成物理地址,即可直接转移。当k远小于2n时,可采用分段的方法,将n个信息标识中的一部分用作矢量地址,以减少对程序存储器的占用。
(4)便于多进程切换的指令能力
上述间址移机制,不但可以支持数据驱动的程序控制,也适宜于按时间片分配进程运行。当系统分配给该进程的时间用完,进入高优先级的系统定时器中断。此时,堆栈顶保存的是被中断进程的断点地址,只要将其作为该进程的下次入口地址保存起来,并执行完该进程的断点保护工作后,再递增指针,指向下一进程的入口地址,即可在定时器中断返回之后,自动将下进程投入运行。
(5)支持循环任务队列的功能
并发运行的多任务,数目会发生变化。微控制器应提供支持循环任务队列的指令,例如前面所说的指针增减一等于某值转移指令,可实现任意位置与长度的循环队列管理,便于正反双向遍历。对于多任务处理,各进程所需的循环队列长度会不同。如果指令格式规定比较值必须是固定的常数,则必须为不同的进程编写惟有比较值不同而功能完全一样的代码段,显然并合理。较好解决方法是间址寄存器支持访问变量。
(6)二级指针管理寄存器块
一些常用的内部存储单元可组成工作组的形式,用二级指针指明当前工作组。在多进程并发运行时,这种方式可加快数据切换等断点保护和恢复工作,并减少指令。
上述指令,在有些微控制器的指令集,已有体现,在此提出,供编制实时多任务应用程序设计者在选用微控制器时参考。有些指令尚未实现,出来供微控制器设计者参考。
随着微电子技术的发展,这些指令的功能并非难以实现,只是要在功能与功能、功能与成本之间进行权衡,或许只能在某些高档的微控制器中才能支持。随着专用系统概念的增强,适用于实地多任务系统应用的微控制器,将使得应用系统设计者更灵活、更迅速地开发出低成本、高性能的产品。