任务介绍

从任务的存储结构来看,uCOS-II的任务由三个组成部分构成:任务程序代码,任务堆栈和任务控制块。其中,任务控制块用来保存任务属性;任务堆栈用来保存任务工作环境;任务程序代码是任务的执行部分。

uCOS-II的任务组成

uCOS-II的任务有两种:用户任务和系统任务。由应用程序设计者编写的任务,叫做用户任务;由系统提供的任务叫做系统任务。用户任务是为解决应用问题而编写的;系统任务是为应用程序来提供某种服务的。

目前uCOS-II可支持多达64个任务(包括用户任务和系统任务)进行管理。

为了管理上的方便,uCOS-II把每一个任务都作为一个节点,然后把它们链接成下图所示的一个任务链表。

uCOS-II的任务在内存中的结构

任务的状态:

因为在嵌入式系统中只有一个CPU,所以在一个具体时刻只能允许一个任务占用CPU。根据任务是否占用CPU,以及是否处于被中断,等待等情况,任务在uCOS-II中可能处于下图5种状态之一。

任务的5种状态

任务在不同状态之间的转换:

任务状态的转换

用户任务代码的一般结构

根据嵌入式系统任务的工作特点,任务的执行代码通常是一个无限循环结构,并且在这个循环中可以响应中断,这种结构也叫做超循环结构。

一个用C语言编写的任务(超循环结构的任务示意性代码):

void MyTask( void *pdata )

{

for(;;)

{

可以被中断的用户代码;

OS_ENTER_CRITICAL();    //进入临界段(关中断)

不可以被中断的用户代码;

OS_EXIT_CRITICAL();       //退出临界段(开中断)

可以被中断的用户代码;

}

}

从程序设计的角度来看,一个uCOS-II任务的代码就是一个C语言函数.为了可以传递各种不同类型的数据甚至是函数,任务的参数是一个void类型的指针.

为了有效地对中断进行控制,在任务的代码里可使用uCOS-II定义的宏OS_ENTER_CRITICAL()和OS_EXIT_CRITICAL()来控制任务何时响应中断,何时屏蔽中断。在运行这两个宏之间的代码时是不会响应中断的,这种受保护的代码段叫做临界段。在具体应用中可以根据实际需要在一个任务中使用这对宏设置多个临界段。

因此可以说,uCOS-II任务的代码结构是一个带有临界段的无限循环。

用户应用程序的一般结构

从程序代码上来看,用户任务似乎就是一个C语言函数,但是这个函数不是一般的C语言函数,它是一个任务(线程)。因此,它不是被主函数或其他函数调用的,主函数main()只负责创建和启动它们,而由操作系统负责来调度运行它们。从代码上来看,用户应用程序的代码大体上如下面所示:

用户应用程序的结构。

void MyTask1( void *pdata )     // 定义用户任务1

{

for(;;)

{

......

}

}

void MyTask2( void *pdata )     // 定义用户任务2

{

for(;;)

{

......

}

}

void MyTask3( void *pdata )     // 定义用户任务3

{

for(;;)

{

......

}

}

void main()

{

......

OSInit();               //初始化uCOS-II

......

OSTaskCreate(MyTask1,......);     //创建用户1

OSTaskCreate(MyTask2,......);     //创建用户2

OSTaskCreate(MyTask3,......);     //创建用户3

......

OSStart();                    //启动任务

......

}

系统任务

uCOS-II预定义了两个为应用程序服务的系统任务: 空闲任务和统计任务。其中空闲任务是每个应用程序必须使用的,而统计任务则

是应用程序可以根据实际需要来选择使用的。

空闲任务

在多任务系统运行时,系统经常会在某个时间内无用户任务可运行而处于所谓的空闲状态。 为了使CPU在没有用户任务可执行

时有事可做,uCOS-II提供了一个叫做空闲任务OSTaskIdle()的系统任务。空闲任务的代码如下:
    
    void OSTaskIdle( void *pdata)
    {
          #if OS_CRITICAL_METHOD == 3
            OS_CPU_SR cpu_sr;
         #endif
 
          pdata = pdata;  //防止某些编译器报错

for(;;)
         {
            OS_ENTER_CRITICAL();  //关闭中断
            OSIdleCtr++;   //计数
            OS_EXIT_CRITICAL();  //开放中断
          }
    }

这里有一行代码为 pdata = pdata,之所以安排了这样一行代码,是因为在这个任务中没有用到参数pdata。对于某些C编译器,在对代

码进行编译时会对这种情况报错(说定义了参数却没有使用),有了这行代码,编译器就不会报错了。
从上面的代码中可以看到,这个空闲任务几乎不做什么事情,只是对系统定义的一个空闲任务运行次数计数器OSIdleCtr进行加1操作。

当然,如果用户认为有必要,那么也可在空闲任务中编写一些做用户工作的代码。
   uCOS-II规定,一个用户应用程序必须使用这个空闲任务,而且这个任务是不能用软件来删除的。

统计任务

uCOS-II提供的另一个系统任务是 统计任务OSTaskStat()。这个统计任务 每秒计算一次CPU在单位时间内被使用的时间,并把计算结

果以百分比的形式存放在变量OSCPUUsage中,以便应用程序通过访问它来了解CPU的利用率,所以该系统任务OSTaskStat()叫做统计任

务。

用户应用程序是否使用统计任务,用户可以根据应用程序的实际需要来进行选择。如果用户应用程序要使用这个统计任务,则必须把定义在系统头文件OS_CFG.H中的系统配置常数OS_TASK_STAT_EN设置为1,并且必须在创建统计任务之前调用函数OSStatInit()对统计任务进行初始化。

 

任务的优先权及优先级别

前面已提及uCOS-II的每个任务都必须具有一个惟一的优先级别。uCOS-II把任务的优先权分为64个优先级别,每一个级别都用一个数字来表示。数字0表示任务的优先级别最高;数字越大则表示任务的优先级别越低。

通常一个应用程序的任务数小于64。为了节省内存,用户可以根据应用程序的需要,在文件OS_CFG.H中通过给表示最低优先级别的常数OS_LOWEST_PRIO赋值的方法,来说明程序中任务优先级别的数目。该常数一旦被定义,就意味着系统中可供使用的优先级别为0,1,2,...,OS_LOWEST_PRIO,共OS_LOWEST_PRIO+1个。同时也限制了应用程序中任务的总数最多不能超OS_LOWEST_PRIO+1个。固定地,系统总是把最低优先级别OS_LOWEST_PRIO自动赋给空闲任务。如果应用程序中还使用了统计任务,则系统会把优先级别OS_LOWEST_PRIO-1自动赋给统计任务,因此用户任务可以使用的优先级别是0,1,2,...,OS_LOWEST_PRIO-2,共OS_LOWEST_PRIO-1个。

例:

如果希望应用程序中任务的优先级别为28个,则表示最低优先级别的常数OS_LOWEST_PRIO值应该是多少?如果应用程序中使用了系统提供的空闲任务和统计任务,则该应用程序最多可以安排多少个任务?

答:表示最低优先级别的常数OS_LOWEST_PRIO值应该为27,优先级别分别为0,1,2,3,...,27;由于系统空闲任务占用了优先级别27,统计任务占用了优先级别26,则应用程序中最多可以安排优先级别分别为0,1,2,...,25的26个任务。

给某一个用户任务的定义优先级别,需要在调用系统函数OSTaskCreate()来创建任务时,用该函数的第4个参数prio来指定。
  由于每个任务都具有惟一的优先级别,因此uCOS-II通常也用任务的优先级别来作为这个任务的标识。

http://blog.csdn.net/sunrier/article/details/6462335

http://blog.csdn.net/sunrier/article/details/6462637

任务应用实例

基于linux平台的ucos 2.86应用程序示例如下:主要是根据ucos中的API创建俩个简单的task。
其代码结构为:

#include <stdio.h>
#include <stdlib.h>
#include "ucos_ii.h"  /* Function common to all tasks */  void MyTask( void *p_arg )
{  char* sTaskName = (char*)p_arg;  #if OS_CRITICAL_METHOD == 3   OS_CPU_SR     cpu_sr = 0;
#endif  while(1)  {  /* printf uses mutex to get terminal access, therefore must enter critical section */  OS_ENTER_CRITICAL();  printf( "Name: %s\n", sTaskName );  OS_EXIT_CRITICAL();  /* Delay so other tasks may execute. */  OSTimeDly(50);  }/* while */  }
int main (void)
{  /* pthreads allocates its own memory for task stacks. This UCOS linux port needs a minimum stack size in order to pass the function information within the port. */  INT8U Stk1[ OSMinStkSize() ];  INT8U Stk2[ OSMinStkSize() ];  char sTask1[] = "Task 1";  char sTask2[] = "Task 2";  OSInit();  OSTaskCreate( MyTask, sTask1, (void*)Stk1, 4 );  OSTaskCreate( MyTask, sTask2, (void*)Stk2, 5 );  OSStart();  return 0;
}  

上面的运行的结果类似如下:

http://blog.csdn.net/suiyuan19840208/article/details/11850065

uCOS-II的任务介绍相关推荐

  1. 51单片机中使用ucos ii的优缺点(好文)

    摘要:近年来,在单片机系统中嵌入操作系统已经成为人们越来越关心的一个话题.本文通过对一种源码公开的嵌入式实时操作系统ucos ii的分析,以51系列单片机为例,阐述了在单片机中使用该嵌入式操作系统的优 ...

  2. lwip协议栈在linux运行,LwIP协议栈在uCOS II下的实现

    1.概述: LwIP协议栈在设计时就考虑到了将来的移植问题,因此把所有与硬件.OS.编译器相关的部份独立出来,放在ucosii&LwIPsource etlwiparch目录下.因此LwIP在 ...

  3. 用C语言写ucos中断服务程序,在ARM处理器上移植uCOS II的中断处理

    uCOS II是一个源码公开.可移植.可固化.可剪裁和抢占式的实时多任务操作系统,其大部分源码是用ANSI C编写,与处理器硬件相关的部分使用汇编语言编写.总量约200行的汇编语言部分被压缩到最低限度 ...

  4. UCOS II移植到STM32F103开发板

    早期嵌入式开发没有嵌入式操作系统的概念 ,直接操作裸机,在裸机上写程序,比如用51单片机基本就没有操作系统的概念.通常把程序分为两部分:前台系统和后台系统. 简单的小系统通常是前后台系统,这样的程序包 ...

  5. ucos II任务管理之一:挂起任务

    Ucos II 任务管理之一 创建好了任务之后,就已经初步跨进了ucos II 的编程了.随着进一步的编程,发现学会创建了任务还是不够的. 在我的项目里,需要实现485通信功能,我创建了任务1用于串口 ...

  6. ucos II任务管理之三:删除任务

    ucos II任务管理之三:删除任务 有了前面的经历之后,mcu21决定全面地学习了任务的管理.这样在项目编程中才能做到"信手拈来". 在ucos II 里,创建一个任务之后,可以 ...

  7. ucos II 创建第一个任务之一

    Ucos II创建第一个任务 我们已经从远处欣赏过ucos II 的身材,现在可以近距离地欣赏Ucos II性感的局部了. 任务是什么? 有一句话:CPU不同的时刻段总是在执行着优先级最高的任务.所以 ...

  8. 基于STM32的简易示波器的UCOS II嵌入式实时操作系统实现

    基于STM32的简易示波器的UCOS II嵌入式实时操作系统实现 在基于STM32的示波器的实现的基础上,在STM32上移植UCOS II嵌入式实时操作系统. 在UCOS II操作系统中将各个功能分发 ...

  9. ucos ii堆栈大小检测

    在使用ucos ii时经常会有疑问,这个堆栈该给多大,虽然ucos ii 自带了任务堆栈检测,但是我觉得太麻烦了,而且还会占用资源,我投机取巧的使用内存是否为0来判断堆栈是否使用过,进而检测出堆栈的最 ...

  10. IAR中移植UCOS II系统以及sourceInsight 使用

    ucos 学习笔记 1 sourceInsight 使用 CSDN参考链接 新建工程 第一步:project中new project 第二步:在高亮部分输入工程的地址,工程文件夹与IAR工程文件夹放在 ...

最新文章

  1. 厦门理工计算机研究生调剂,2018年厦门理工大学考研预调剂信息公布
  2. 如何优雅的使用 Angular 表单验证
  3. SimpleAdapter类使用方法
  4. 计算机基础应用的培养活动记录,小学少年宫计算机兴趣小组活动记录表
  5. sasmgr get_info -D /dev/sasd1 -q raid 查看RX6600 硬件 raid 信息
  6. Guava Cache 使用笔记
  7. BZOJ1233: [Usaco2009Open]干草堆tower
  8. python将图片转换成手绘_利用Python生成手绘效果的图片
  9. 计算机单位换换算,时间单位换算表与计算机单位换算
  10. LOVE2D android竖屏的问题
  11. 多元线性回归--案例分析及python实践
  12. 开利完成对广东积微集团的收购; 正威国际与中润超油建设全球最大规模的石墨烯润滑材料生产基地和研发中心 | 能动...
  13. 360浏览器出现https证书错误怎么办
  14. 港股招股书“失效”无需过度解读 专业人士:不影响IPO进程
  15. 爱快路由器使用L2TP线路做出口
  16. 思科下一代模拟器EVE-NG镜像导入
  17. [python]遍历字典dict的几种方法
  18. 解决VS在Release下编译程序报“应用程序无法启动,应用程序的并行配置不正确”的问题
  19. van访谈_谷歌业务分析师访谈
  20. 2019 Multi-University Training Contest 5

热门文章

  1. gluLookAt 函数详解
  2. OSI七层模型个人理解
  3. 详解Socket接口
  4. iOS中响应者链条-触摸事件,hitTest方法坐标转换
  5. 筛选Fiddler的URL 并且标记背景颜色用法
  6. k8s集群——Deployment
  7. Vue 图书管理案例
  8. 食品行业的新科技总结
  9. 中科院考研经历⑥--暑假总结及下学期计划
  10. 8.23恒指/德指/做单思路导图及晚盘前瞻