刚开始接触
uCOS
的同学有可能不了解信号量的意思,云里雾绕。其实说白了,信号量就是操作系统提供的一种数据通信方式,他相当于一把钥匙,可以在不同任务之间进行通信,告诉其他任务是否可以执行了。比如任务 A
满足一定的条件需要执行任务 B
, 那么任务 A
可以在自己的任务函数中释放一个信号量,任务 B
等到这个信号量之后,便觉得有信号了,好,我可以运行了。 uCOS
提供了以下几个信号量相关的函数:
OSSemCreate() OSSemDel () OSSemPend () OSSemPost () OSSemAccept() OSSemQuery()
其中,我们常用的只有三个即 OSSemCreate ()
、 OSSemPend()
、 OSSemPost()
。 在 uCOS
中,信号量的结构为: ``` typedef struct os_event { INT8U OSEventType; void *OSEventPtr; INT16U OSEventCnt; OS_PRIO OSEventGrp; OS_PRIO OSEventTbl[OS_EVENT_TBL_SIZE]; } OS_EVENT; ```
可以看到其中有个 OSEventCnt
,这是一个计数器,用来统计任务中某一资源被占用的情况。如果资源被占用,则该计数器由操作系统减一。 一般信号量可以有两种,二值互斥型以及计数型。怎么理解呢?互斥型就是说这个资源在同一时刻只能被一个任务所使用,比如用串口发送数据,这个串口在同一时刻只能发送一个任务的数据,否则会造成数据紊乱,对于这种情况,就可以创建互斥信号量:
OSSemCreate(1)
参数1
表示这个资源只有一个,任何任务都必须等待这个资源空闲的时候才能使用。还有一种计数型的信号量,比如串口接收数据,接收到一个数据,我们加 1
,也就是 OSEventCnt++
,这样的信号量为计数型,在串口接收完数后,可以查看该信号量的值,来判断串口接收到的数据长度。
ucos等待信号量机制
OSSemPend()
函数为等待信号量,其格式为
OSSemPend (Sem,0,&err)
Sem
是我们定义的信号量,0
代表无限期等待下去,如果其他任务没有释放信号量,那么本任务将暂停在这句等待信号量语句这,当然也可以自己设置超时,如等待1s
,等不到信号量则根据err错误信息的情况执行相应的语句。
等待机制简单理解:程序暂停,别的任务一旦释放信号量,本任务在优先级调度后立刻执行。
v v v v v v
本文为作者原创,请勿转载,转载请联系作者。
点击下方卡片,关注我的公众号,有最新的文章和项目动态。
v v v v v v