用户登录  |  用户注册
首 页商业源码原创产品编程论坛
当前位置:PB创新网文章中心解决方案电子通信

uC/OS-II的任务切换机理及中断调度优化

减小字体 增大字体 作者:佚名  来源:本站整理  发布时间:2009-01-11 00:03:54
到图4中③的SP位置。接着,系统会查询到优先级最高的任务,然后把SP的指针移到优先级最高的任务的任务堆栈,进行R15~R4的出栈工作,最后用RETI中断返回指令返回到新的任务。因为我们把所有的任务堆栈都规定成相同的格式,所以它们之间不会产生问题。这里需要注意的是,因为系统在C编译器的中断处理中会对中断进入时默认压栈的寄存器出栈,所以在设计出栈的程序时,要先把这些内容压栈,这样才能正确出栈。

  2)在中断的处理过程中,有别的中断产生,产生中断嵌套。

  如图5所示,由于在处理中断的时候,SP已经被移到系统堆栈去了,只有当中断退出的时候才可能把SP移到别的任务的任务堆栈中。所以在中断的时候进行中断嵌套,那么对于中断的处理和第一次是一样的,所不同的是,这次保存在堆栈中的不是任务运行中的寄存器,而是中断处理中的寄存器,而且是保存在系统堆栈中而不是任务堆栈中。从这里就可以看出优化内存的效果。所有的中断嵌套中的寄存器压栈都压在系统堆栈中,这样对于任务堆栈内存大小的要求大大降低。
javascript:window.open(this.src);" style="cursor:pointer;"/>
  因为μC/OS-II在进入中断中,会把全局变量OSIntNesting++;在退出中断的时候,又会把OSIntNesting--。在退出中断进行任务切换之前,μC/OS-II会先判断OSIntNesting是否为0,是0才会进行任务调度。当第二中断运行结束以后,退出中断嵌套的时候,OSIntNesting不为0,也就不会进行任务调度。因此,仍旧在系统堆栈出栈,那么系统会继续前面没有完成的中断服务程序。

  接着退出中断的顺序和非中断嵌套的顺序是一样的。在中断处理完以后,SP会自动回到图4中③的SP位置。接着,系统会查询到优先级最高的任务,然后把SP的指针移到优先级最高的任务的任务堆栈。进行R15~R4的出栈工作,最后用RETI中断返回指令返回到新的任务。

  中断的情况基本上就是上述两种。对于有些文献中提到的在中断中会调度到更高优先级的任务的情况,笔者觉得是不应该发生的。因为从上面的分析可以看出,默认的(μC/OS-II的设计思路)中断处理会同时对全局变量OSIntNesting进行增减处理,javascript:window.open(this.src);" style="cursor:pointer;"/>以给出是否需要任务调度的条件。那么即使在中断服务程序中把更高优先级的任务就绪,也会等到中断退出以后再进行调度,除非是在中断中直接调用更高优先级的任务函数。但这种方法应该是和μC/OS-II的原则相违背的,沿用的是以前前后台设计的思路。

  对于这样的设计方式,时钟节拍的处理方式必须和一般的中断处理方式是一样的。一般来说,MSP430使用WATCHDOG时钟中断作为时钟节拍的产生源。从本质上来说,时钟节拍本身也是中断处理过程,所以对于时钟节拍的处理应该和其它的中断处理过程相同。实际上,在时钟节拍的处理过程中也可能会存在中断嵌套的问题。

  中断堆栈和任务堆栈分离设计的程序流程如图6所示。

4 几点建议

  ① 编写中断程序的时候,有条件尽量使用汇编语言。因为这样可以避免一些编译器自己进行的操作,减少指针调整的次数。

  ② 在用C编写中断服务的时候,因为有些功能必须调用汇编的函数才能实现。调用函数时,有些时候压栈的PC会破坏堆栈的结构。这个时候需要把堆栈进行适当的调整,保证堆栈格式的正确。

  ③ 中断处理过程中调用OSIntExit()的时候,由于 μC/OS-II的原始设计中SP指针有时是不调整的,所以在OSIntExit()返回了以后,还要判断一下是否中断嵌套。因为有的时候是需要切换任务的。



上一页  [1] [2] [3] 

Tags:

作者:佚名

文章评论评论内容只代表网友观点,与本站立场无关!

   评论摘要(共 0 条,得分 0 分,平均 0 分) 查看完整评论
PB创新网ourmis.com】Copyright © 2000-2009 . All Rights Reserved .
页面执行时间:29,859.38000 毫秒
Email:ourmis@126.com QQ:2322888 蜀ICP备05006790号