微波EDA网,见证研发工程师的成长!
首页 > 硬件设计 > 嵌入式设计 > ucOS- II中设计了五种通讯机制

ucOS- II中设计了五种通讯机制

时间:11-27 来源:互联网 点击:
在ucOS- II中设计了五种通讯机制,或者说是同步机制,分别是信号量(semaphore),互斥体(mutual exclusion semaphore),事件组(event flag),邮箱(message box)和队列(queue),而事件(event)则是这几种通讯机制的核心,这几天学习了一下这几种机制,总结一下先,呵呵。

1. 先总结一下作为核心的事件控制机制:

1.1 数据结构设计:类似于任务就绪表一样,作者设计了等待任务表,表的作用原理和任务就绪表完全一样,甚至共用了OSMapTbl和OSUnMapTbl这 两个表,不用之处,任务就绪表用来查询就绪的任务中优先级最好的那个,而等待任务表用来查询等待事件的任务中优先级最高的那个,类似于就绪表,设计了两个 变量:OSEventGrp和OSEventTbl[],不同的时候这两个变量被设计进时间控制块(event control block ECB)中,也就是说对于每个事件(上述五种)都有一个等待任务表。对于ECB,还有其他三个变量:OSEventType(用来标识是上述五种的哪一 种), OSEventCnt(信号量和互斥体会用到)和OSEventPtr(在邮箱中用来存放消息,在队列中用来存放队列块的指针)。对于事件组来说,作者设 计了另一套数据结构,而没有用到ECB。

1.2 事件控制的核心函数有四个,基本上就是对等待任务表的操作,这些函数将作为上述五种通讯机制的核心功能:

1.2.1OS_EventWaitListInit:初始化等待任务表, 很简单。

1.2.2 OS_EventTaskRdy:首先找到等待该事件的优先级最高的任务,将其从等待任务表中移走,然后更新该任务的TCB,最高根据TCB的OSTCBStat变量更新任务就绪表(如果该任务没有等待任何事件,那么就把它加入任务就绪表)。

1.2.3 OS_EventTaskWait:首先把当前任务从任务就绪表中移走,然后把当前任务加进这个事件的等待任务表。这个函数其实就是挂起当前任务!

1.2.4 OS_EventTO:超时处理函数,将当前任务从等待任务列表中移走,并更新TCB使其进入就绪状态,值得注意的是,它并不更新就绪任务表!!!

2. 信号量的实现

信号量的用途主要有三个:第一, 表示一个或多个事件的发生; 第二, 表示共享资源的可用(二值信号量); 第三, 表示n个相同资源的访问(多值信号量)(这是书上的说法,我认为应该表述为: 表示共享资源对n个任务的可用)。

2.1 数据结构设计:信号量只是用到ECB,一个信号量用一个ECB表示,没有用到其他数据结构。其中ECB的OSEventPtr变量没有用到,只是简单的将其设为0,因此信号量是比较简单的一个通讯机制。

2.2 核心函数主要有四个:

2.2.1 OSSemCreate:创建一个信号量:首先从事件控制块缓冲区中得到一个ECB,然后初始化这个ECB,对其中等待任务表的初始化用到OS_EventWaitListInit。

2.2.2 OSSemDel:销毁一个信号量:有两种情况, 第一,只有在没有任务等待该信号量的时候才删除;第二,不管有没有任务等待该信号量都强制删除;对于第一种情况,用OS_DEL_NO_PEND进行标 识,这个时候,如果确实没有任务在等待该信号量,将ECB归还到ECB缓冲区,然后返回; 如果有任务在等待该信号量,直接返回错误标识,以告诉调用者删除失败。 对于第二种情况,用OS_DEL_ALWAYS进行标识,首先用OS_EventTaskRdy将等待任务表中的所有任务都移走,然后将该ECB归还到 ECB缓冲区。这个时候要做判断如果刚刚有任务在等待该信号量(这个判断在移走之前已经做好),就必须重新调度:OS_Sched!所以,如果当前任务不是优先级最高的任务,那么这个函数将会被挂起,呵呵。

2.2.3 OSSemPend:该函数可能会引起当前任务被挂起:首先判断该信号量是否可用,也就是ECB的OSEventCnt是否不为0,如果可用的话更新 ECB然后返回,任务继续执行;如果不可用,那么就更新当前任务的TCB,然后用OS_EventTaskWait挂起任务,然后重新调度。这时,该函数 将可能被挂起,直到当前任务获得该信号量从而恢复执行。然后该函数判断当前任务继续执行的原因,如果是超时的话,调用OS_EventTO,如果是得到信 号量而返回的话,更新当前TCB,然后返回。另外,这也就是OS_EventTO不更新就绪表的原因——本身已经在运行了呀,呵呵。

2.2.4 OSSemPost:该函数释放该信号量,从而可以使正在等待该信号量的任务恢复执行: 首先判断等待任务表中是否有任务正在等待该信号量,如果有的话就通过OS_EventTaskRdy使等待任务表中优先级最高的任务不再等待该信号量(具 体的操作如上面所述)。接下来(不管有没有任务正在等待该信号量)就更新ECB,其实就是将其中的变量OSEventCnt加1。

前面对信号量 做

Copyright © 2017-2020 微波EDA网 版权所有

网站地图

Top