当前位置: 首页 > news >正文

简单理解:FreeRTOS 中,信号量(Semaphore)函数及其作用

在 FreeRTOS 中,信号量(Semaphore) 是一种用于任务间同步或资源计数的机制,本质上是一个受保护的整数,通过对其进行 “获取”(减 1)和 “释放”(加 1)操作实现任务间的协调。信号量主要分为二进制信号量(值为 0 或 1)和计数信号量(值为 0 到最大计数),适用于不同场景。

信号量的作用

  1. 任务同步实现任务间的事件通知(如 “生产者 - 消费者” 模型):一个任务完成操作后释放信号量,唤醒等待该信号量的另一个任务。例如,传感器数据就绪后,中断服务程序(ISR)释放信号量,唤醒处理数据的任务。

  2. 资源计数限制同时访问某资源的任务数量(计数信号量)。例如,限制最多 3 个任务同时使用某个硬件外设,信号量初始值为 3,每个任务获取信号量(减 1)后使用资源,释放时加 1。

  3. 事件标志作为事件发生的标志,任务通过等待信号量判断事件是否发生(二进制信号量常用此场景)。

常用信号量函数

1. 创建信号量
(1)二进制信号量(初始值 0 或 1)
SemaphoreHandle_t xSemaphoreCreateBinary(void);
  • 功能:创建二进制信号量,初始值为 0(需先调用xSemaphoreGive使其变为 1)。
  • 若需初始值为 1(类似互斥锁初始状态),可使用:

    SemaphoreHandle_t xSemaphoreCreateBinaryStatic(StaticSemaphore_t *pxSemaphoreBuffer);
    
    (静态创建,需手动初始化值为 1)。
(2)计数信号量
SemaphoreHandle_t xSemaphoreCreateCounting(UBaseType_t uxMaxCount,  // 最大计数(信号量允许的最大值)UBaseType_t uxInitialCount  // 初始计数
);
  • 例如:xSemaphoreCreateCounting(5, 3) 表示最大计数 5,初始值 3。
2. 获取信号量(阻塞方式)

任务尝试获取信号量(信号量值减 1),若值为 0 则阻塞等待。

BaseType_t xSemaphoreTake(SemaphoreHandle_t xSemaphore,  // 信号量句柄TickType_t xTicksToWait        // 阻塞等待时间(tick数,0表示不等待,portMAX_DELAY表示永久等待)
);
  • 返回值:pdPASS 成功(信号量值≥1,减 1 后返回);errQUEUE_EMPTY 超时失败(信号量始终为 0)。
3. 释放信号量(任务中使用)

任务释放信号量(信号量值加 1),唤醒等待该信号量的任务。

BaseType_t xSemaphoreGive(SemaphoreHandle_t xSemaphore  // 信号量句柄
);
  • 返回值:pdPASS 成功(信号量值未达最大值,加 1 后返回);errQUEUE_FULL 失败(计数信号量已达uxMaxCount)。
4. 中断中释放信号量

在中断服务程序(ISR)中释放信号量(不可阻塞)。

BaseType_t xSemaphoreGiveFromISR(SemaphoreHandle_t xSemaphore,BaseType_t *pxHigherPriorityTaskWoken  // 输出参数:若为pdTRUE,需触发任务切换
);
  • 功能:中断安全版本的释放函数,无阻塞时间,适合在 ISR 中通知任务(如数据就绪)。
5. 删除信号量
void vSemaphoreDelete(SemaphoreHandle_t xSemaphore);
  • 功能:释放信号量占用的内存,删除后句柄失效。

注意事项

  1. 二进制信号量 vs 计数信号量

    • 二进制信号量:值只能是 0 或 1,适合同步(如事件通知),类似 “开关”。
    • 计数信号量:值可在 0 到uxMaxCount之间,适合资源计数(如限制并发访问数量)。
  2. 与互斥锁的区别

    • 信号量无 “优先级继承” 机制,不适合保护共享资源(可能导致优先级反转)。
    • 互斥锁是特殊的二进制信号量,带优先级继承,专门用于资源保护;普通信号量更适合同步。
  3. 中断中的使用限制

    • 中断中只能使用xSemaphoreGiveFromISR释放信号量,不能调用xSemaphoreTake(因可能阻塞,中断需快速执行)。
  4. 信号量的所有权信号量可以由任意任务或中断释放(无需与获取者一致),而互斥锁必须由获取它的任务释放。

信号量是 FreeRTOS 中灵活的同步工具,二进制信号量适合任务间事件通知,计数信号量适合资源并发控制,需根据场景选择使用。

http://www.dtcms.com/a/569249.html

相关文章:

  • 【计算机网络】IO复用方法(三)——poll
  • 企业门户网站建设方案及报价广告网名
  • 【海思】在Ubuntu20.04上搭建可以成功编译Hi3559AV100的环境_20251104
  • Vue中iFrame跨窗口通信实现与源码解析
  • 做设计有哪些接私活的网站做钓鱼网站获利3万
  • git常用的指令-(工作中常用)
  • <数据集>yolo航拍交通目标识别数据集<目标检测>
  • 做标准件网站在ppt里面做网站链接
  • 关于网站建设的调研报告电商专业就业前景
  • 做百度糯米网站的团队做的比较好的个人网站
  • 天津市建设厅官方网站网站用绝对路径好还是相对路径seo
  • DevExpress WPF v25.2新功能预览 - 支持将JetBrains Rider与报表设计器集成
  • 力扣热题100道之102二叉树的层序遍历
  • SQLite Truncate Table: 完全删除表中的数据
  • 机器学习:数据集的划分
  • 学校网站建设费计入什么科目wordpress拖曳组件
  • 中国城乡和住房建设部网站wordpress微信商城
  • 零基础学JAVA--Day23(final关键字+抽象类及应用模板设计模式)
  • Linux虚拟机配置jupyter环境并在宿主机访问
  • 低空无人机“一网统飞”深度解构:从技术内核到产业落地,重构低空经济操作系统
  • MyBatis 中 resultMap、association、collection标签详解
  • 网站长期建设运营计划书自己怎么健网站视频下载
  • 网站强制qq弹窗代码专业网页设计制作价格
  • QuickRedis
  • 微信小程序开发案例 | 个人相册小程序(上)
  • JAVA多商户家政同城上门服务预约服务抢单派单+自营商城系统支持小程序+APP+公众号+h5
  • ELK 学习笔记
  • 在 Ubuntu 上快速配置 Node.js 环境(附问题说明)
  • discuz修改网站关键词wordpress微信qq登陆
  • 钦州公司做网站网络空间安全专业大学排名