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

从零玩转RT-Thread(19):

本课时介绍如何让任务睡眠,从而让任务暂停运行指定的时间。

为什么要延时

在实际项目中,我们经常会用到让任务睡眠相关的接口,从而实现以下功能。

  • 避免CPU占用过多(如忙等)
  • 控制执行节奏(如LED闪烁、采样周期)
  • 给其他任务运行机会

工作原理

当任务需要睡眠时,RT-Thread会将其加入到定时器列表里。这样一来,任务就不会参与调度,无法运行。

只有当任务睡眠时间结束时,任务才会从定时器列表移回就绪队列。

相关接口

在RT-Thread中,与睡眠相关的接口如表所示:

函数名

说明

rt_thread_mdelay(ms)

毫秒级延时(常用)

rt_thread_delay(tick)

等同于rt_thread_sleep()

rt_thread_sleep(tick)

tick数延时,单位为系统节拍数

rt_thread_delay_until(&tick, inc_ticks)

从*tick开始的时间,睡眠inc_ticks时间

其中,rt_thread_mdelay()以毫秒为单位,其余函数以系统时钟节拍周期为单位。该周期由如下配置宏来决定:

#define RT_TICK_PER_SECOND 1000

示例代码:每秒闪烁 LED

下面给出了一个简单的示例,展示了部分睡眠函数的作用。

#include <rtthread.h> #include "base.h" void task1_entry(void *param) { RT_UNUSED(param); while (1) { rt_kprintf("Task 1 is running\n"); rt_thread_delay(RT_TICK_PER_SECOND); // 延时1秒 } } void task2_entry(void *param) { RT_UNUSED(param); rt_tick_t ticks = rt_tick_get(); while (1) { rt_kprintf("Task 2 is running\n"); rt_thread_delay_until(&ticks, RT_TICK_PER_SECOND); } } int main(void) { hardware_init(); rt_thread_t t1 = rt_thread_create( "t1", task1_entry, RT_NULL, 1024, 20, // 相同优先级 20 // 时间片为5个tick ); rt_thread_t t2 = rt_thread_create( "t2", task2_entry, RT_NULL, 1024, 20, // 相同优先级 40 ); if (t1) rt_thread_startup(t1); if (t2) rt_thread_startup(t2); return 0; }

注意事项

睡眠的时间精度取决于系统时钟节拍周期

RT-Thread 使用系统时钟节拍定时器来周期性触发任务调度。该时钟节拍由RT_TICK_PER_SECOND宏配置。

假设RT_TICK_PER_SECOND=1000,那么一个tick时间= 1ms。也就说,此时睡眠的最小单位就是 1 Tick。

如果调用睡眠时间的函数时间点卡得不够好,则可能睡眠过多或过多少,具体如下图所示。

从上图可以看出,实际的睡眠时间比期望的要短或长一些,但是差距不超过一个tick(假设任务在睡眠完之后,能够立即运行)

而如果有其它任何干扰,如更高优先级的任务抢占CPU、同优先级其它任务正在运行,则实际延时时间要更长一些。

因此,在 RTOS 中我们说延时是“近似的、最小保证的延时”,不能用于精密定时(如 1ms 级别的 PWM 控制),而应使用硬件定时器或定时器中断实现更高精度的控制。

课程推荐

  • 全新升级的手写RTOS课程:从原理到实战,一次掌握操作系统的核心

  • 用10000+行代码手写一个TCP/IP协议栈

  • 硬核项目,从0手搓一个RISC-V模拟器!

作者介绍 李述铜,嵌入式系统与底层架构领域讲师,专注于操作系统、CPU 架构、RTOS 内核与系统软件实现原理的教学与研究。 出版作品《从0手写x86计算机操作系统》,主讲课程包括:《从0手写嵌入式操作系统》《从0手写TCP/IP协议栈》《从0手写FAT32文件系统》等。

http://www.cnnetsun.cn/news/18364.html

相关文章:

  • 从零玩转RT-Thread(20):为什么需要定时器?——定时器的应用场景
  • eino框架结构化输出解析:从混乱文本到精准数据的魔法转换
  • 小爱音箱终极音乐解放方案:XiaoMusic完整使用指南
  • 从零打造专业级Vue滑块控件:vue-slider-component深度实践指南
  • AnuPpuccin主题深度体验:5个技巧让你的Obsidian笔记焕然一新
  • AI一键搞定!Linux安装JDK17的最佳实践
  • Win11Debloat:释放系统潜能,打造专属纯净Windows体验
  • Python Web开发终极指南:用Ludic框架重构你的前端体验
  • F2批量重命名终极指南:从入门到精通的完整解决方案
  • 深蓝词库转换工具的技术架构与应用实践
  • 2025年CLIP模型爆发:从跨模态基座到产业变革的技术革命
  • 腾讯混元图像3.0登顶全球!800亿参数重构AIGC行业格局
  • halcon求区域交集——intersection
  • 如何用5分钟掌握AMD Ryzen处理器深度调试技巧?终极完整教程
  • 终极Nginx Web界面管理指南:从入门到精通的一站式解决方案
  • 收藏!大模型推理核心:从Prefill到KVCache,小白也能懂的底层逻辑
  • PySceneDetect终极指南:零基础实现智能视频场景自动化分割
  • 5分钟搞定Windows应用拦截:效率提升指南
  • 基于VUE的线上签到系统[VUE]-计算机毕业设计源码+LW文档
  • 深度解析vue-slider-component:打造高度定制化的Vue滑块组件
  • Pose-Search终极指南:开启智能人体姿势识别新纪元
  • 基于VUE的文章发布系统[VUE]-计算机毕业设计源码+LW文档
  • BBDown:B站视频下载的终极解决方案
  • Dify企业级实战深度解析 (5)
  • 游戏增强工具YimMenu:从入门到精通的完整指南
  • B站视频下载神器:BiliDownloader完全使用手册
  • 如何快速合并分割APK:开源工具的终极解决方案指南
  • 实时语音转写技术革命:WhisperLiveKit如何重塑语音交互体验
  • 基于海马体突触修剪机制的动态剪枝策略在量化交易系统中的实现
  • 【毕业设计/课程设计】桃树种植环境检测系统系统源码+论文+PPT+数据