关闭
搜索
搜索
本版
帖子
用户
热搜:
程序员
简洁模式
高级模式
用户组: 游客
消息
提醒
新听众
我关注的
帖子
道具
勋章
任务
设置
退出
请
登录
后使用快捷导航
没有帐号?
立即注册
设为首页
收藏本站
开启辅助访问
切换到窄版
登录
or
立即注册
快捷导航
搜索
首页
论坛
BBS
MCU单片机技术
程序员交流
UCOSIII信号量和互斥信号量
[复制链接]
作者:
劫_Zed
版块:
›
灌水·股票·程序员大本营·工作之余需要点阳光·我们不只是工程师
›
IT业界资讯
发布时间:
2019-2-22 10:05:59
786
0
返回列表
劫_Zed
当前离线
新手上路
新手上路, 积分 4, 距离下一级还需 46 积分
新手上路
新手上路, 积分 4, 距离下一级还需 46 积分
积分
4
发消息
楼主
电梯直达
劫_Zed
发表于 2019-2-22 10:05:59
|
只看该作者
|
倒序浏览
|
阅读模式
在UCOSIII中在某一时刻可能会有多个任务来访问共享资源,信号量最早来控制任务访问共享资源,信号量现在也被用来实现任务间的同步以及任务和中断处理函数ISR的同步。在例如UCOSIII这个可剥夺的内核中,当任务独占信号量来使用共享资源时,就会出现低优先级任务先于高优先级任务运行的现象,即这种现象是
优先级反转
。优先级反转这个现象不应该在UCOSIII中出现,因为它违反了UCOSIII可剥夺的特性,所以为了解决优先级反转这个问题,UCOSIII引入了互斥信号量。。。。。。
本文讲解一下UCOSIII信号量和互斥信号量。
信号量
信号量相当于一种上锁机制,任务的代码必须要获得相应的信号量钥匙后才能执行,只要获得信号量,就意味着该任务具有进入被锁部分代码的权限,一旦执行到被锁代码段,任务就一直处于等待状态,知道对应被锁部分代码的钥匙被再次释放再执行。
信号量有两种类型:二进制信号量和计数型信号量,其中二进制信号量只能取0,1两个值,就像逻辑中的是与非,而计数型信号量不止可以取两个值,在共享资源中,只有任务才能使用信号量,在中断服务函数不能使用信号量,避免出现阻塞。
二进制信号量
某个资源对应的信号量为1时,就可以使用这个资源,相反,如果对应的资源的信号量为0,那么等待该信号量的任务就会被放进等到信号量的任务表中,在等待信号量的时候也可以设置超时时间,如果等待时间超过设置的超时时间,那么就意味着任务没有等待到信号量,此任务就会进入就绪态,任务以发信号的方式来操作信号量。若信号量为二进制信号量时,一次只能一个任务使用共享资源。
计数型信号量
在同时有多个任务要访问共享资源时,二进制信号量就不能使用了,我们转而使用计数型信号量,例如一个信号量初始化值为10,则表示只有前10个请求该信号量的任务可以使用该共享资源。之后的新任务需要等待前10个任务释放掉该信号量。每次只要有任务请求该信号量时,信号量值就会减1,直至0. 反之有任务释放掉该信号量后,信号量的值就会加1.
这里,列举了信号量的API函数,在之后的实验里都会使用到:
OSSemCreate() :创建一个信号量
OSSemDel() :删除一个信号量
OSSemPend() :等待一个信号量
OSSemPendAbort(): 取消等待
OSSemPost():释放一个信号量
OSSemSet() :强制设置一个信号量值(不建议)
要使用信号量,就必须在之前创建一个信号量,在UCOSIII中使用函数OSSemCreate()来创建信号量,函数原型如下:
参数:
p_sem
:指向信号量的控制块,首先在调用此函数之前先定义一个全局信号量,则p_sem存放的是信号量的指针。OS_SEM SEM.
p_name
:信号量的名字
cnt
: 设置信号量的初始值,如果该值设置为1,则表示此信号量使用的是二进制信号量,若此值大于1,则使用的是计数型信号量。
p_err:
保存调用此函数后返回的错误码
。
请求信号量
当一个任务需要独占式的访问某个特定的系统资源时,需要与其他任务或中断服务程序同步,或者需要等待某个事件的发生,应该调用函数OSSemPend(),原型如下:
参数:p_sem:指向一个信号量的指针。
timeout:指定等待信号量的超时时间(时钟节拍),若在指定时间内没有信号量则恢复任务执行,若此参数为0,则任务一直等待,直到等到信号量。
opt:选项:OS_OPT_PEND_BLOCKING:指定信号量无效时,任务挂起来等待信号量。
OS_OPT_PEND_NON_BLOCKING:信号量无效时,任务直接返回。
p_ts:指向一个时间戳
p_err:错误码。
发送信号量
任务获得信号量以后就可以直接访问共享资源了,在任务访问完共享资源后则必须释放信号量,释放信号量也叫发送信号量,使用函数OSSemPost()发送信号量。若没有任务在等待该信号量,则OSSemPost()只是简单将信号量加1,然后返回调用该函数的任务中继续运行。如果有一个或者多个任务在等待这个信号量,则优先级最高任务获得这个信号量。后做任务切换。
OSSemPost
():
p_sem:指向一个信号量指针。
opt:选择信号量发送的方式:
OS_OPT_POST_1:仅向等待该信号量优先级最高的任务发送信号量。
OS_OPT_POST_ALL:向等待该信号量所有任务发送信号量。
OS_OPT_POST_NO_SCHED:禁止在本函数使用任务调度。
互斥信号量
为了避免优先级反转问题,UCOSIII支持一种特殊的二进制信号量:互斥信号量。
只有任务才能使用互斥信号量,且任务最多可对该互斥信号量嵌套使用250次。
这里,列举了互斥信号量的API函数
OSMutexCreate():创建一个互斥信号量
OSMutexDel():删除一个互斥信号量
OSMutexPend():等待一个互斥信号量
OSMutexPendAbort():取消等待
OSMutexPost():释放互斥信号量
如果占用互斥信号量的任务比当前申请该互斥信号量的任务优先级低的话,OSMutexPend()函数会将占用互斥信号量的任务优先级暂时提升到当前申请任务的优先级,当最后释放掉互斥信号量时,再重新恢复之前的优先级。
本帖子中包含更多资源
您需要
登录
才可以下载或查看,没有帐号?
立即注册
收藏
0
相关帖子
•
北京招聘:卡斯柯招聘(央企,住房及户口可解决,入职5险一金)
•
Linux负载均衡算法有瑕疵,修复后性能将提升一倍
•
Linux之父怒删工程师提交的补丁,称“太蠢了”网友:怼得好!
•
Linux系统编程—时序竞态
•
linux后台开发中避免僵尸进程的方法总结
•
在脚本中使用Bash信号捕获|Linux中国
•
STM32通过软件模拟IIC驱动温湿度传感器HTU21D
•
Ansible自动化工具安装、配置和快速入门指南|Linux中国
•
【每天学点新知识】Linux操作系统下C语言多线程同步使用指南!
•
这些Linux的“自动化”技巧,教你轻松完成任务
回复
使用道具
举报
返回列表
高级模式
B
Color
Image
Link
Quote
Code
表情
@朋友
您需要登录后才可以回帖
登录
|
立即注册
本版积分规则
发表回复
回帖后跳转到最后一页
浏览过的版块
招聘&找工作
生活交流*灌水区*工程师滋润生活*
快速回复
返回顶部
返回列表