目前常见的嵌入式软件系统架构有三种可以分为:轮询系统架构、前后台系统架构和多任务系统架构。
1、轮询系统架构
轮询系统架构是最简单的一种软件结构,主程序是一段无限循环的代码,在循环中顺序查询各个条件,如果满足就执行相应的操作。
这种方案的好处是实现简单,逻辑清晰,便于开发人员掌握。但是每个事件的查询和处理时间是不能确定的,假如前面的操作时间较长,那么后面的操作必然会被延迟。
如下图所示,假如步骤1操作需要很久,那么步骤2必然得不到及时处理,如果步骤2的工作很重要或者很紧急,那么系统的性能和响应能力就很差了。
示例伪代码如下所示:
int main(void){ HwInit(); //初始化外设 while(1) { statement_1; //语句1 statement_2; //语句2 statement_3; //语句3 ...... } return 0;}
2、前后台系统架构
相对轮询系统架构,前后台系统架构对外部事件的处理做了优化,前后台系统架构是由中断驱动的。
主程序依然是一段无限循环的代码,称为后台程序,而事件的响应则由中断来完成,称为前台程序。
在后台程序执行时,如果有外部事件发生,则前台的中断程序会打断后台程序。在完成必要的事件响应之后,前台中断程序退出并通知后台程序来继续操作,由后台程序完成事件的后继处理。
从代码功能上讲,事件的响应和处理分为了两个部分。因为中断自身有优先级和嵌套的功能,所以优先级高的事件能够得到及时响应。但后台程序仍然需要按顺序处理各个事件的后继事务。
在中断源之间有优先级的概念,ISR会首先响应事件,简单的事件可以在ISR中直接处理,复杂的情况下则记录下必要数据和状态标记,等所有中断处理结束后,将由后台主函数按顺序处理各个事件。也可以理解,事件的响应是支持优先级的,但事件的最终处理却是顺序的。
使用中断来代替轮询方案中事件的查询操作,对事件的响应能力有较大改善。
示例伪代码如下所示:
int main(void){ HwInit(); //初始化外设 while(1) { statement_1; //语句1 statement_2; //语句2 statement_3; //语句3 ...... } return 0;} void interrupt_event(void) { statement_4; //语句4 return 0;}
3、多任务系统架构
相对于前后台系统架构,多任务系统架构在响应事件的时候,同样是由多个中断处理程序完成的。但是对于事件的后继操作则是由多个任务来处理的,也就是说每个任务处理它所负责的事件。
在基于优先级的多任务系统架构中,因为任务间存在优先级高、低的关系,优先级高的任务可打断低优先级任务的运行而取得CPU的优先使用权,这样优先级高的事件就能及时得到处理;在基于分时机制的多任务系统中,任务间则按比例轮流占用处理器。
因为多任务系统架构允许将具体的应用系统分成若干个相对独立的任务来管理,所以多任务操作系统的使用可以简化应用程序的设计,系统也变得简洁且便于维护和扩展。对实时性要求严格的事件都能得到及时可靠的处理。不过多任务操作系统自身将消耗更多的处理器、存储器等硬件资源,这是引入多任务机制的必要代价。
示例伪代码如下所示:
int main(void){ HwInit(); //初始化外设 OS_Init(); //初始化系统 OS_Start(); //运行内核调度 while(1) { ...... } return 0;} //任务1void task_1(void){ task_statement_1; task_statement_2; task_statement_3; OS_delay();} //任务2void task_2(void){ task_statement_1; task_statement_2; task_statement_3; OS_delay();} //任务3void task_3(void){ task_statement_1; task_statement_2; task_statement_3; OS_delay();}
4、区别
最后,对比一下三种嵌入式软件系统架构的特点和区别,如下表所示: