第2章-μCOS与μCOS-II的任务part1教材课件

上传人:无*** 文档编号:241672791 上传时间:2024-07-14 格式:PPT 页数:34 大小:2.63MB
返回 下载 相关 举报
第2章-μCOS与μCOS-II的任务part1教材课件_第1页
第1页 / 共34页
第2章-μCOS与μCOS-II的任务part1教材课件_第2页
第2页 / 共34页
第2章-μCOS与μCOS-II的任务part1教材课件_第3页
第3页 / 共34页
点击查看更多>>
资源描述
1二、uC/OS与uC/OSII的任务2第二章:uC/OS与uC/OSII的任务目标:本章旨在向学员介绍uC/OS-II实时操作系统及uC/OS-II的任务,通过本章的学习,学员应该掌握如下知识:uC/OS-II的结构及特点 任务堆栈 任务控制块、就绪表 任务的操作 uC/OS-II初始化后的数据结构学时:学时:9.09.0学时学时教学方法:讲授教学方法:讲授pptppt上机练上机练习点评案例分析习点评案例分析32.1 2.1 uC/OS简介简介q uC/OS是JeanJ.Labrosse开发的一个高度可移植的实时 操作系统。q uC/OS是一种基于优先级的可抢先的硬实时内核。q 它是一种专门为嵌入式设备设计的内核。4嵌入式硬件平台BSPKERNELKERNELFSFSTCP/IPTCP/IP设备驱动设备驱动设备设备I/OI/O其它组件其它组件应用RTOS内存管理内存管理事件管理事件管理通信管理通信管理时间管理时间管理2.1.1 关于RTOS图2-1 RTOS5公开源代码可移植性(Portable)绝大部分C/OS的源码是用移植性很强的ANSI C写的。和微处理器硬件相关的那部分是用汇编语言写的。汇编语言写的部分已经压到最低限度,使得 C/OS便于移植到其他微处理器上。C/OS可以在绝大多数8位、16位、32位以至64位微处理器、微控制器、数字信号处理器(DSP)上运行可固化(ROMable)C/OS是为嵌入式应用而设计的,这就意味着,只要读者有固化手段(C编译、连接、下载和固化),C/OS可以嵌入到读者的产品中成为产品的一部分。可裁剪(Scalable)可以只使用C/OS中应用程序需要的那些系统服务。也就是说某产品可以只使用很少几个C/OS调用,而另一个产品则使用了几乎所有C/OS的功能,这样可以减少产品中的C/OS所需的存储器空间(RAM和ROM)。这种可剪裁性是靠条件编译实现的。2.1.2 uC/OS的性能特点6多任务占先式(Preemptive)C/OS可以管理64个任务,然而,目前这一版本保留8个给系统。应用程序最多可以有56个任务可确定性 全部C/OS的函数调用与服务的执行时间具有可确定性。任务栈 每个任务有自己单独的栈,C/OS允许每个任务有不同的栈空间,这样可以 加快任务调度的速度。系统服务 C/OS提供很多系统服务,例如邮箱、消息队列、信号量、块大小固定的内存的申请与释放、时间相关函数等。中断管理 中断可以使正在执行的任务暂时挂起,如果优先级更高的任务被该中断唤醒,则高优先级的任务在中断嵌套全部退出后立即执行,中断嵌套层数可达255层。稳定性与可靠性2.1.2 uC/OS的性能特点(续)117q全世界有数百种产品在应用 AvionicsMedicalCell phonesRouters and switchesHigh-end audio equipmentWashing machines and dryersUPS(Uninterruptible Power Supplies)Industrial controllersGPS Navigation SystemsMicrowave RadiosInstrumentationPoint-of-sale terminals更多2.1.3 uC/OS的各种商业应用图2-2 UC/OS应用8v信号量v带互斥机制的信号量v优化优先级倒置的问题v消息信箱v消息队列v内存管理v时钟管理v任务管理2.1.4 uC/OS提供的系统服务92.1.5 uC/OSII 内核结构图2-3 UC/OSII内核结构应用程序(用户代码)C/OS-II(与处理器无关代码)OS_CORE.cOS_FLAG.c.C/OS-II配置(与应用无关)OS_CFG.HINCLUDES.H C/OS-II移植(与处理器相关代码)CPU定时器 硬件软件用于产生系统时钟移植时需要编写的代码,包含了与处理器相关的代码定义所有与内核裁减有关的宏定义及主头文件内核部分,包括了所有内核代码和系统功能代码102.1.5 uC/OSII 内核结构(续)介绍source insight查看代码工具,建立一个工程,添加源码,另外将显示字号调整大。1、INCLUDES.H、CONFIG.H是按实际配置需要而改变的。2、Test.c是用户的应用程序。3、ucos与用户代码是混合编译到一起的,内核代码可见。4、OS_CPU.H、OS_CPU_A.ASM、OS_CPU_C.C是与处理器(硬件)相关代码,从X86平台移植到51或者ARM等都需要改写。5、PC.H是借用DOS资源显示试验结果而书写的BC45编译器识别的函数,不是ucos的文件。该部分不需学习。112.2 2.2 uC/OSII的任务的任务前一个任务控制块的指针后一个任务控制块的指针指向任务堆栈的指针任务的优先级别voidmytask(void*pdata)for(;)任务的代码 任务控制块 任务堆栈 任务图2-4 任务的组成从任务存储结构来看,由三部分构成:任务程序代码、任务堆栈和任务控制块。任务控制块用来保存任务属性,任务堆栈用来保存任务工作环境,任务程序代码是任务的执行部分注:任务控制块和任务代码间接的关联起来12任务代码任务控制块任务堆栈 任务1任务代码任务控制块任务堆栈 任务2任务代码任务控制块任务堆栈 任务3任务代码任务控制块任务堆栈 任务n图2-5 任务链表2.2.1 uC/OS的任务uC/OS-II的任务有两种:用户任务和系统任务。由应用程序设计者编写的任务叫做用户任务,由系统提供的任务叫做系统任务。用户任务是为解决应用问题而编写的,系统任务是为应用程序来提供某种服务的。目前,uC/OS-II最多可以对64个任务(包括用户任务和系统任务)进行管理。132.2.2 任务的状态图2-6 任务的状态线上的函数作用:状态迁移依靠这些函数完成14因为在嵌入式系统中只有一个CPU,所以在一个具体时刻只能允许一个任务占用CPU。根据任务是否占用CPU,以及是否处于被中断、等待等情况,任务可能出于以下5种状态之一:睡眠睡眠态(DORMANTDORMANT):任务在没有被配备任务控制块或被剥夺了任务控制块时的状态叫作任务的睡眠态。就就绪态(READYREADY):如果系统为任务配备了任务控制块且在任务就绪表中进行了就绪登记,则任务就具备了运行的充分条件,这时的任务的状态叫就绪态。运行运行态(RUNNINGRUNNING):):处于就绪态的任务如果经调度器判断获得了CPU的使用权,则任务就进入运行态。任何时刻只能有一个任务处于运行态。等待等待态(WAITINGWAITING):):正在运行的任务,需要等待一段时间或需要等待一个事件发生再运行时,该任务就会把CPU的使用权让给其他任务而使任务进入waiting状态。注:进入waiting的状态有可能是因为延时,有可能是被挂起,有可能是等待的资源未获得,总之,uC/OS将所有的已经注册了的但未就绪的任务归为waiting态。被中断被中断态(ISRISR):):正在运行的任务是可以被中断的,除非该任务将中断关了,或者uC/OS-将中断关了。被中断了的任务就进入了中断服务态(ISR)。当所有的任务都在等待事件发生或等待延迟时间结束,uC/OS-执行空闲任务(idle task),执行OSTaskIdle()函数。2.2.2 任务的状态(续)152.2.3 用户任务代码的一般结构void MyTask(void*pdata)for(;)可以被中断的任务代码;OS_ENTER_CRITICAL();/进入临界段(关中断)不可以被中断的任务代码;OS_EXIT_CRITICAL();/退出临界段(开中断)可以被中断的任务代码;OSTimeDly(10);根据嵌入式系统任务的工作特点,任务的执行代码通常是一个无限循环结构,并且在这个循环中可以响应中断,这种结构也叫超循环结构。为了有效的对中断进行控制,在任务的代码里可使用UC/OS-II定义的宏OS_ENTER_CRITICAL()和OS_EXIT_CRITICAL()来控制何时响应中断,何时屏蔽中断。在运行这两个宏之间的代码时是不会响应中断的,这种受保护的代码段叫临界段。162.2.3 用户应用程序一般结构(续)(初步展现用户代码结构)void Task1(void*pdata)/定义用户任务1 for(;)void Task2(void*pdata)/定义用户任务2 for(;)void main()OSInit();/初始化uC/OS-II OSTaskCreate(Task1,);/创建用户任务1 OSTaskCreate(Task2,);/创建用户任务2 OSStart();/启动任务 从代码来看,用户任务似乎就是一个C语言函数,但是这个函数不是一般的C语言函数,他是一个任务。因此它不是被主函数或其它函数调用的,主函数main()只负责创建和启动它们,而由操作系统负责来调度运行它们。使用函数OSStart()启动任务之后,任务就交由操作系统管理和调度了。17void OSTaskIdle(void*pdata)pdata=pdata;for(;)OS_ENTER_CRITICAL();OSIdleCtr+;OS_EXIT_CRITICAL();OSTaskIdleHook();4 C/OS-II总是要建立一个空闲任务(idle task),这个任务在没有其它任务进入就绪状态时投入运行。空闲任务永远为最低优先级。用户控制,可写入用户代码(如进入低功耗等),但决不能调用使该任务挂起的函数,因为这个任务要永远处于就绪状态。2.2.4 系统任务之空闲任务uC/OS-II预定义了两个为应用程序服务的系统任务:空闲任务和统计任务。其中空闲任务是每个应用程序必须使用的,而统计任务则是应用程序可以根据实际需要来选择使用的。空闲任务不能被应用程序删除。空闲任务只是做了一个计数工作注意!空闲任务中没有调用任务延时函数18qOSTaskStat()每秒运行1次,计算CPU利用率,即告诉用户应用程序使用了多少CPU时间,用百分比表示,精确度为1%。q如果将系统头文件OS_CFG.H中的系统配置常数OS_TASK_STAT_EN设置为1,统计任务就会在操作系统初始化函数OSInit()中调用OS_InitTaskStat()函数创建建。q在系统调用多任务启动函数OSStart()之前,用户初始代码中必须先建立至少一个用户任务(如TaskStart),如果应用程序打算使用统计任务,需要在TaskStart任务中调用函数OSStatInit()对统计任务进行初始化初始化。之后再建立应用程序中的其他任务。q应该在这个用户任务中(第一个任务)启动时钟节拍。因为用户不希望在多任务还没有开始时就收到时钟节拍中断。2.2.5 系统任务之统计任务19void main(void)OSInit();/初始化uC/OS-II /*创建用户起始任务(以TaskStart()作为起始任务,也可以创建多个任务)*/OSStart();/开始多任务调度void TaskStart(void*pdata)/*在这里安装并启动uC/OS-II的时钟节拍*/OSStatInit();/初始化统计任务 /*创建用户应用程序任务*/for(;)/*这里是TaskStart()的代码*/OSTimeDly(10);2.2.5 系统任务之统计任务(续)202.2.6 任务的优先级quC/OS-II分为64个优先级别,每一个级别都用一个数字表示。数字0的级别最高,数字越大优先级别越低。q通常,一个应用程序的任务数小于64,用户可根据应用程序的需要,在OS_CFG.H中设置OS_LOWEST_PRIO,即定义了可供使用的优先级别共OS_LOWEST_PRIO+1个。q固定地,系统总是把最低优先级别自动赋给空闲任务,如果系统中还有统计任务,则其优先级别为OS_LOWEST_PRIO-1。21&思考题2-1:如果希望应用程序中任务的优先级别为28个,则表示最低优先级别的常数OS_LOWEST_PRIO值应该是多少?如果应用程序中使用了系统提供的空闲任务和统计任务,则该应用程序最多可以安排多少个任务?给某一个用户任务定义优先级别,需要在调用系统函数给某一个用户任务定义优先级别,需要在调用系统函数OSTaskCreate()OSTaskCreate()来创来创建任务时,用该函数的第建任务时,用该函数的第4 4个参数个参数prioprio来指定。来指定。由于每个任务都具有唯一的优先级别,因此由于每个任务都具有唯一的优先级别,因此uC/OS-IIuC/OS-II通常也用任务的优先级别来作为这个任通常也用任务的优先级别来作为这个任务的标示。务的标示。222.2.7 任务堆栈p所谓堆栈,就是在存储器中按数据“后进先出(LIFO)”的原则组织的连续存储空间。为了满足任务切换和响应中断时保存CPU寄存器中的内容及存储任务私有数据的需要,每个任务都应该配有自己的堆栈。任务堆栈是任务的重要组成部分。232.2.7.1 任务堆栈的创建为方便定义任务堆栈,在文件OS_CPU.H中专门定义了一个数据类型OS_STK:typedef unsigned int OS_STK;/该类型长度为16位这样,在应用程序中定义任务堆栈的栈区就非常简单,即定义一个OS_STK类型的一个数组即可。例如:#define TASK_STK_SIZE 512 /定义堆栈长度(1024字节)OS_STK TaskStkTASK_STK_SIZE;/定义一个数组来作为任务堆栈创建任务函数OSTaskCreate()原型如下:INT8U OSTaskCreate(void(*task)(void*pd),/指向任务的指针 void*pdata,/传递给任务的参数 OS_STK*ptos,/任务堆栈栈顶的指针 INT8U prio);/指定任务优先级别的参数当调用函数OSTaskCreate()来创建一个任务时,把堆栈数组的指针传递给函数OSTaskCreate()中的堆栈栈顶参数ptos,就可以把该数组与任务关联起来而成为该任务的任务堆栈。24&思考题2-2:创建一个任务MyTask,堆栈的长度为128字节,优先级别为20,任务参数pdata的实参为ttt(指针变量)。试写出需要的代码。#define MyTaskStkN64OS_STK MyTaskStkMyTaskStkN;void main(void)OSTaskCreate(MyTask,ttt,&MyTaskStkMyTaskStkN-1,20);252.2.7.1 任务堆栈的创建(续)堆栈的增长方向是随系统所使用的处理器不同而不同。因此在使用函数OSTaskCreate()创建任务时,一定要注意所使用的处理器对堆栈增长方向的支持是向上的还是向下的。高地址低地址堆栈增长的方向向上堆栈增长的方向向下图3-7 堆栈的不同增长方向上一练习时假设使用了支持堆栈向下增长方式的处理器设置参数ptos。如果使用的处理器支持堆栈的增长方向向上,则应该为:OSTaskCreate(MyTask,&ttt,&MyTaskStk0,20);为了提高应用程序的移植性,在编写代码时可兼顾两种情况,利用OS_CFG.H文件中的常数OS_STK_GROWTH作为选择开关,使用户可通过定义该常数的值来选择相应代码段,以适应不同的堆栈增长方向的需要。试改写上一练习代码。262.2.7.2 任务堆栈的初始化uC/OS-II在创建任务函数OSTaskCreat()中通过调用任务堆栈初始化函数OSTaskStkInit()来完成任务堆栈初始化工作的,其原型如下:OS_STK*OSTaskStkInit(void(*task)(void*pd),void*pdata,OS_STK*ptos,INIT16U opt);由于各处理器的寄存器及对堆栈的操作方式不同,因此该函数需要用户在进行uC/OS-II的移植时,按所使用的处理器由用户来编写。当CPU启动运行一个任务时,CPU的各寄存器总是需要预置一些初始数据,例如指向任务的指针、任务堆栈指针、程序状态字等。那么,系统启动任务时,CPU从何处可以获得这些数据呢?最方便的方法就是让CPU从这个任务的任务堆栈里获得这些数据!27q一旦任务建立,一个任务控制块OS_TCB就被赋值。q任务控制块是一个数据结构,保存该任务的相关参数,包括任务堆栈指针,任务的当前状态,任务的优先级等。q任务CPU使用权被剥夺时,TCB保存该时刻任务状态;任务重新得到CPU控制权时,TCB确保任务从当时被中断的那一点丝毫不差地继续执行。qOS_TCB全部驻留在RAM中。2.2.8 任务控制块(TCB)及任务控制块链表任务控制块就相当于一个任务的身份证,没有任务控制块的任务是不能被系统承认和管理的。282.2.8.1 任务控制块的结构typedef struct os_tcb OS_STK *OSTCBStkPtr;/指向当前任务堆栈栈顶的指针。每个任务的堆栈容量可以是任意的。#if OS_TASK_CREATE_EXT_EN void *OSTCBExtPtr;/指向任务控制块扩展的指针,扩展功能:任务执行时间、任务切换次数、任务堆栈使用情况等。OS_STK *OSTCBStkBottom;/指向当前任务堆栈栈底的指针。INT32U OSTCBStkSize;/任务堆栈的长度 INT16U OSTCBOpt;/创建任务时的选择项 INT16U OSTCBId;/用于存储任务的识别码。保留。#endif struct os_tcb*OSTCBNext;/指向后一个任务控制块的指针 struct os_tcb*OSTCBPrev;/指向前一个任务控制块的指针#if(OS_Q_EN&(OS_MAX_QS=2)|OS_MBOX_EN|OS_SEM_EN OS_EVENT *OSTCBEventPtr;/指向事件控制块的指针#endif#if(OS_Q_EN&(OS_MAX_QS=2)|OS_MBOX_EN void *OSTCBMsg;/指向传递给任务消息的指针#endif INT16U OSTCBDly;/任务等待的时限 INT8U OSTCBStat;/任务的当前状态标志 INT8U OSTCBPrio;/任务的优先级别 INT8U OSTCBX;/用于快速访问就绪表的数据 INT8U OSTCBY;/用于快速访问就绪表的数据 INT8U OSTCBBitX;/用于快速访问就绪表的数据 INT8U OSTCBBitY;/用于快速访问就绪表的数据#if OS_TASK_DEL_EN BOOLEAN OSTCBDelReq;/请求删除任务时用到的标志#endif OS_TCB;29任任务控制控制块结构的主要成构的主要成员到本到本节为止需要熟知的成止需要熟知的成员!typedefstructos_tcbOS_STK *OSTCBStkPtr;/指向任务堆栈栈顶的指针struct os_tcb*OSTCBNext;/指向后一个任务控制块的指针struct os_tcb*OSTCBPrev;/指向前一个任务控制块的指针INT16U OSTCBDly;/任务等待的时限(节拍数)INT8U OSTCBStat;/任务的当前状态标志INT8U OSTCBPrio;/任务的优先级别OS_TCB;30两条两条链表来管理任表来管理任务控制控制块:空任务块链表(所有任务控制块还没有分配给任务),是在应用程序调用函数OSInit()对系统进行初始化时建立的。任务块链表(所有任务控制块已经分配给任务),是在调用函数OSTaskCreate()创建任务时建立的。建立任务控制块链表的具体做法是,从空链表摘取一个空任务控制块,然后填充上任务属性后再形成新的链表。312.2.8.2 任务控制块链表图2-8 空任务块链表OSTCBNextOSTCBPrevOSTCBPrioOSTCBNextOSTCBPrevOSTCBPrioOSTCBNextOSTCBPrevOSTCBPrioOSTCBNextOSTCBPrevOSTCBPrioOSTCBNextOSTCBPrevOSTCBPrioOSTCBNextOSTCBPrevOSTCBPrioOSTCBTbl0OSTCBTbl1OSTCBTbl2OSTCBTbl3OSTCBTblOS_MAX_TASKS+OS_N_SYS_TASK_-2OSTCBTblOS_MAX_TASKS+OS_N_SYS_TASK_-1OSTCBFreeList系统在调用函数OSInit()对uC/OS-II系统进行初始化时,先在RAM中建立一个OS_TCB结构类型的数组OSTCBTbl,每个数组元素就是一个任务控制块,然后把这些控制块链接成一个如图所示的链表。由于链表中的这些控制块还没有与具体任务相关联,因此这个链表叫做空任务块链表。每当应用程序调用系统函数OSTaskCreate()创建一个任务时,系统就会将任务控制块链表头指针OSTCBFreeList指向的任务控制块分配给该任务。在给任务控制块中的各成员赋值后,就按任务控制块链表的头指针OSTCBList将其加入到任务控制块链表中。322.2.8.2 2.2.8.2 任务控制块链表任务控制块链表(续续)OSTCBNextOSTCBPrevOSTCBPrio=3OSTCBNextOSTCBPrevOSTCBPrio=1OSTCBNextOSTCBPrevOSTCBPrioOSTCBNextOSTCBPrevOSTCBPrioOSTCBNextOSTCBPrevOSTCBPrioOSTCBNextOSTCBPrevOSTCBPrioOSTCBTbl3OSTCBTbl3OSTCBTbl2OSTCBTbl2OSTCBTbl4OSTCBTbl4OSTCBTbl0OSTCBTbl0OSTCBTbl1OSTCBTbl1OSTCBTblOS_MAX_TASKS+OS_N_SYS_TASK_-1OSTCBTblOS_MAX_TASKS+OS_N_SYS_TASK_-1OSTCBListOSTCBList0 0OSTCBFreeListOSTCBFreeList0 0OSTCBPrioTblOSTCBPrioTbl00112233OS_MAX_TASKS+OS_N_SYS_TASK_-2OS_MAX_TASKS+OS_N_SYS_TASK_-2OS_MAX_TASKS+OS_N_SYS_TASK_-1OS_MAX_TASKS+OS_N_SYS_TASK_-1OSTCBCurOSTCBCur图图2-9 2-9 任务控制块链表和任务控制块链表和OSTCBPrioTblOSTCBPrioTbl数组及变量数组及变量OSTCBCurOSTCBCur数据类型为OS_TCB*。专门存放正在运行的任务的任务控制块指针保存控制块指针的数组数据类型为OS_TCB*。专门用来以任务的优先级别为顺序在各个数组元素里存放指向各个任务控制块的指针。任务任务删除删除的原理?的原理?F 0 0332.2.8.3 任务控制块的初始化当用户程序调用函数OSTaskCreate()创建一个任务时,这个函数会调用系统函数OS_TCBInit()来为任务控制块进行初始化。这个函数首先为被创建任务从空任务控制块链表获取一个任务控制块,然后利用任务的属性对任务控制块各个成员进行赋值,最后再把这个任务控制块链入到任务控制块链表的头部。初始化任务控制块函数OSTCBInit()的原型如下:INT8U OSTCBInit(INT8UPrio,/任务的优先级别,保存在OSTCBPrio中OS_STK*ptos,/任务堆栈栈顶指针,保存在OSTCBStkPtr中OS_STK *pbos,/任务堆栈栈底指针,保存在OSTCBStkBottom中INT16Uid,/任务的标示符,保存在OSTCBId中INT16Ustk_size,/任务堆栈的长度,保存在OSTCBStkSize中void*pext,/任务控制块的扩展指针,保存在OSTCBExtPtr中INT16Uopt/任务的控制块的选择项,保存在OSTCBOpt中);34
展开阅读全文
相关资源
正为您匹配相似的精品文档
相关搜索

最新文档


当前位置:首页 > 管理文书 > 施工组织


copyright@ 2023-2025  zhuangpeitu.com 装配图网版权所有   联系电话:18123376007

备案号:ICP2024067431-1 川公网安备51140202000466号


本站为文档C2C交易模式,即用户上传的文档直接被用户下载,本站只是中间服务平台,本站所有文档下载所得的收益归上传人(含作者)所有。装配图网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对上载内容本身不做任何修改或编辑。若文档所含内容侵犯了您的版权或隐私,请立即通知装配图网,我们立即给予删除!