标签:调度 业务逻辑 查询 init oid fun 问题 实时 erp
本文在21IC的公众号文章《多年嵌入式编程工程师经验分享:换个角度来编程》基础上结合自己理解而写,部分图片以及文字说明均来自互联网。
当开发过程中不使用OS时,几乎所有的嵌入式程序归根结底都是一个由无法停止的循环为结构构成的,即常见的while(1)
或for(;;)
,用流程图表示就是这样:
这个过程中,软件处在两种状态下:
这种软件设计即前后台设计,用图像表示即:
这种软件设计下可以将设备需要的功能根据实时性进行分类,将实时性要求不高但需要持续刷新的功能作为一个子函数在主循环中顺序执行,而将需要快速响应的功能作为中断函数进行处理。
这种方法存在几个问题:
上面的问题当然有一些解决的办法,但是都不是十分完美:
将中断任务作为一个任务标记函数,并将中断任务进行拆分,中断来临时仅进行任务工作状态标记,如按键等,在主程序中对每个子任务执行前进行状态标记检查:
int main()
{
while (1)
{
if (interflag == 1)
{
subinterfuncs(); //执行中断子程序
}
else
{
backgroundfunc1(); //后台任务1
}
if (interflag == 2)
{
subinterfuncs(); //执行中断子程序
}
else
{
backgroundfunc2(); //后台任务1
}
//后续其他任务等等
}
return 0;
}
subinterfuncs()
{
switch (subinterflag)
{
case 1:
interfunc1(); //中断子任务1
break;
case 2:
interfunc2(); //中断子任务2
break;
default:
break;
}
return;
}
这个方法虽然解决了中断逻辑臃肿的问题,但是只适合于那些触发动作式的场景,例如当按键按下时可以先快速的在屏幕或其他人机交互界面上响应触发的动作,但是该动作并未完全执行,比如在液晶屏上显示“执行中”等,可以先解决响应速度问题,但是对于需要显示完整动作结果的场景依然无法解决。这种情况下可以设计交互流程,提高用户体验。
解决方法跟上面类似,将子任务继续拆分,将长耗时任务拆分,将周期性的时间要求高的任务穿插在长耗时任务中,即在一个循环内高耗时任务总体执行一次,时间要求高的任务执行多次。这种解决方法增加了程序维护成本,并且不是所有的任务都可以被有效拆分,高时效任务的执行周期不固定,因此并不是一个很有效的解决手段。
由于前后台模型在周期性任务上存在上面提到的问题,因此出现了时间片模型来解决这个问题,时间片模型简单地说就是通过时间分割调整不同任务的执行顺序,保证周期性任务时间上的满足:
程序上只需要在循环中执行调度器即可:
/*--------------------主函数-----------------------*/
void main(void)
{
SCH_Init();//设置调度器
SCH_Add_Task(任务函数名,任务调度延迟,任务调度周期);//将任务加入调度器的任务队列
SCH_Start();//刷新任务队列
while(1)
{
SCH_Dispatch_Tasks(); //执行任务调度器
}
}
/*-------------------定时中断函数---------------------*/
Void SCH_Update(void) interrupt
{
//刷新任务队列
}
例如5ms一个周期的任务和100ms一个周期的任务可以通过一个5ms的定时器,通过计数的周期进行判断应该执行哪个任务,这里类似RTOS的任务设计,可以解决前后台模型中任务的时间要求问题。
时间片模型的问题十分明显:
在这种情况下只有将任务进行合理的拆分,设计好程序的执行周期,才可以解决这个问题。
从任务的时效性上可以将所有可执行的任务分为以下三种:
这三类任务中,可以将及时型任务处理放在中断中,并赋予最高的中断优先级,即当及时型任务触发时,其他任务必须暂停。
这里存在一个优先级的过程,如果外部响应的优先级没有定时任务的优先级高,则也可以考虑在执行定时任务时将中断关闭,有限保证定时任务。总之根据实际场景决定优先级
定时型和后台任务由时间片进行调度,定时型任务自己单独享用一个定时器,由该定时器触发时执行定时任务,在执行定时任务时关闭后台型任务的中断,不响应外界输入,当定时任务执行完毕后开启中断,即及时型任务可打断后台型任务。
后台任务由另一个定时器控制时间调度,中断优先级最低,执行过程中中断并不关闭,即可被及时型任务和定时型任务抢断,抢断的优先级取决于场景,如及时任务的优先级高则可在及时任务中将总中断关闭,退出时打开总中断。而当定时任务执行时则将定时器中断关闭,避免后台任务抢占定时任务。
标签:调度 业务逻辑 查询 init oid fun 问题 实时 erp
原文地址:https://www.cnblogs.com/RegressionWorldLine/p/11909331.html