一、信号量实现 访问共享资源
task4 task5共同需要访问共享资源区,都同时请求信号量
其中一个在访问的时候,另一个只能处于等待状态。
//task4、5:使用信号量访问共享资源区 void task4_task(void *p_arg) { OS_ERR err; u8 str1[] = "task4 using share_resource"; while(1) { OSSemPend(&SEM_share_resource,0,OS_OPT_PEND_BLOCKING,0,&err); //等待信号量 请求 memcpy(share_resource,str1,sizeof(str1)); printf("%s\r\n",share_resource); OSSemPost(&SEM_share_resource,OS_OPT_POST_1,&err); //发送信号量 释放 printf("task4_......\r\n"); } } void task5_task(void *p_arg) { OS_ERR err; u8 str2[] = "task5 using share_resource"; while(1) { OSSemPend(&SEM_share_resource,0,OS_OPT_PEND_BLOCKING,0,&err); //等待信号量 请求 memcpy(share_resource,str2,sizeof(str2)); printf("%s\r\n",share_resource); OSTimeDlyHMSM(0,0,5,0,OS_OPT_TIME_PERIODIC,&err); //延时5s,释放对cpu的控制权 OSSemPost(&SEM_share_resource,OS_OPT_POST_1,&err); //发送信号量 释放 } }
二、信号量实现 任务同步
task6 按按键‘上’,实现post信号量,即信号量+1
task7不停地请求一次信号量,如果请求到 OSTimedly 1s后再请求。
//task6、7:使用信号量实现任务同步 void task6_task(void *p_arg) { OS_ERR err; u8 key; while(1) { key = KEY_Scan(0); switch(key) { case WKUP_PRES: OSSemPost(&SEM_task_synchronous,OS_OPT_POST_1,&err); //发送信号量 释放 信号量+1 printf("task6 Sem post = %d \r\n",SEM_task_synchronous.Ctr); break; } OSTimeDlyHMSM(0,0,0,10,OS_OPT_TIME_PERIODIC,&err); //延时5s,释放对cpu的控制权 } } void task7_task(void *p_arg) { OS_ERR err; while(1) { OSTimeDlyHMSM(0,0,5,0,OS_OPT_TIME_PERIODIC,&err); //延时5s,释放对cpu的控制权 OSSemPend(&SEM_task_synchronous,0,OS_OPT_PEND_BLOCKING,0,&err); //等待信号量 请求 printf("task7 Sem pend = %d \r\n",SEM_task_synchronous.Ctr); LED0 = ~LED0; OSTimeDlyHMSM(0,0,1,0,OS_OPT_TIME_PERIODIC,&err);//防止灯闪的太快 看不清 } }
三、信号量会出现 优先级反转 的情况
场景:高优先级、低优先级共同访问一个信号量,中优先级不访问信号量
当一个低优先级任务和一个高优先级任务同时使用同一个信号量,而系统中还有其他中等优先级任务时。
如果低优先级任务获得了信号量,那么高优先级的任务就会处于等待状态,
但是,中等优先级的任务可以打断低优先级任务而先于高优先级任务运行
(此时高优先级的任务在等待信号量 ,所以不能运行),
这时就出现了优先级反转的现象。
文章来源: 【UCOSIII】【信号量】