Freertos学习日志(1)-基础知识
目录
1.什么是Freertos?
2.为什么要学习RTOS?
3.Freertos多任务处理的原理
1.什么是Freertos?
RTOS,即(Real Time Operating System 实时操作系统),是一种体积小巧、确定性强的计算机操作系统。 RTOS 通常用于需要在严格时间限制内对外部事件做出反应的嵌入式系统,如医疗设备和汽车电子控制单元 (ECU)。 通常,此类嵌入式系统中只有一两项功能需要确定性时序,即使嵌入式系统不需要严格的实时反应,使用 RTOS 仍能提供诸多优势。Freertos是RTOS的一种,常用的 RTOS 有国外的FreeRTOS、 μC/OS、RTX 和国内的 FreeRTOS、Huawei LiteOS 和 AliOS-Things 等,其中尤以国外开源 且免费的 FreeRTOS 的市场占有率最高。
2.为什么要学习RTOS?
第一:从一个学生竞赛搞项目的角度而言,掌握RTOS可以使编程更加简单,从学习角度来看RTOS通常比通用操作系统体积更小,重量更轻,更加适用于内存、计算和功率受限的设备,如:STM32。学习RTOS也可以让我们加深对OS(操作系统)的理解。
第二:从一个即将从事嵌入式方向的软件工程师而言,仅仅将所有操作放在一个大循环里,轮询实现问题,当遇到一些轮询机制解决不了的问题时,如果不会RTOS时一定会感到手足无措,而学习RTOS就是解决这类问题的关键!
第三:从本人了解的信息而言,几乎每一个大公司有使用RTOS,有些是使用市面上占有率高的,比如RT-Thread。有些是自己写一套操作系统,所以熟练掌握一套典型的RTOS对于我们至关重要!
3.Freertos多任务处理的原理
1)内核是操作系统的核心组件。Linux 等通用操作系统采用的内核 允许多个用户看似同时访问计算机的处理器。这些用户可以各自执行多个程序,看起来像是并发运行。
每个执行的程序由操作系统控制下的一个或多个线程实现。如果操作系统能够以这种方式执行多个线程,则称为多任务处理。 像 FreeRTOS 这样的小型 RTOS 通常将线程称为任务,因为它们不支持虚拟内存,因此进程和线程之间没有区别。
上面是我从Freertos官网复制的一段话,用我的话来说,RTOS就像是一拳超人动漫中的男主,用自己超强的速度制造出残影,变成影分身一样,RTOS(实时操作系统)就是利用计算机强大的处理能力来处理各种“任务”,也就是制造“影分身”。但是其实“影分身”并不是实体而是“残影”,所以就有了并发运行的说法。
2)调度器是内核中负责决定在特定时间应执行什么任务的部分。内核 可以在任务的生命周期内多次暂停并恢复该任务。 如果任务 B 取代任务 A 成为当前执行的任务 (即任务 A 暂停,任务 B 恢复),我们就可以称任务 A “换出”,任务 B “换入”。
调度策略是调度器用来决定何时执行哪个任务的算法。在(非实时)多用户系统中, 调度策略通常会确保每个任务获得“公平”的处理器时间。实时嵌入式系统中使用的策略详见下文。
只有当调度算法决定执行不同的任务时,任务才会换出。这种切换可能在当前 执行的任务不知情的情况下发生,例如调度算法响应外部事件或定时器到期时; 还可能 发生在执行任务显式调用某个导致其让出、休眠(也称为延迟)或阻塞的 API 函数时。
如果某任务让出,调度算法可能会再次选择同一任务执行。如果某任务休眠, 则在指定的延迟时间到期前不可被选择。 同样,如果某任务阻塞, 则在特定事件发生(例如,数据到达 UART)或超时期满之前将不可被选择。
操作系统内核负责管理这些任务状态和转换, 确保根据调度算法和每个任务的当前状态在给定时间选择适当的任务执行。
参考上图中的数字标记:
在标记 (1) 处,任务 1 正在执行。
在标记 (2) 处,内核将任务 1 换出……
……并在标记 (3) 处将任务 2 换入。
在任务 2 执行期间,在标记 (4) 处,任务 2 锁定了处理器外设以进行独占访问(图中不可见)。
在标记 (5) 处,内核将任务 2 换出……
……并在标记 (6) 处将任务 3 换入。
任务 3 试图访问之前被任务 2 锁定的处理器外设,发现其被锁定,在标记 (7) 处阻塞以等待外设解锁。
在标记 (8) 处,内核将任务 1 换入。
如此往复。
在标记 (9) 处,任务 2 再次执行,完成对外设的操作并解锁。
在标记 (10) 处,任务 3 再次执行,发现外设可用,继续执行直到再次被换出。
实时操作系统 (RTOS) 利用与通用(非实时)系统相同的原理来实现多任务处理, 但两者的目标截然不同。这一差异主要体现在调度策略上。实时嵌入式系统 旨在对现实世界的事件作出及时响应。这些事件通常有截止时间, 实时嵌入式系统必须在此之前响应,RTOS 调度策略必须确保遵守这些截止时间要求。
为在小型 RTOS(如 FreeRTOS)中实现这一目标,软件工程师必须为每个任务分配优先级。RTOS 的调度策略 就是确保能够执行的最高优先级任务获得处理时间。如果存在多个能够运行的同等最高优先级任务(既没有延迟也没有阻塞),则调度策略可以选择在这些任务之间“公平”地分配处理时间。
这种基本形式的实时调度并非万能,无法改变时间的快慢,应用程序编写者必须确保设定的时序约束在所选任务优先级安排下是可行的。
上面的文章也是我从官方文档中复制的,其实从上面的文章中可以看出来,RTOS与通用的系统都使用相同的原理来实现多任务处理,都是抢占式调度,采用快速切换机制,都有优先级的排序。但是他们所要实现的目标完全不同,从而导致RTOS有一个特别的特点——每一个事件都有截止时间。
比如涉及一个带有键盘、LCD 和控制算法的实时系统:
用户每次按键后, 必须在合理的时间内获得视觉反馈,如果用户在此期间无法看到按键已被接受, 则该软件产品的使用感会很差(软实时)。如果最长可接受的响应时间是 100 毫秒,则接受任何介于 0 和 100 毫秒之间的响应。
所以RTOS要求我们软件工程师为控制任务分配最高优先级,因为:
1.控制任务的截止时间比按键处理任务更严格。
2.错过截止时间对控制任务的后果比对按键处理任务更严重。
下图演示了实时操作系统如何调度这些任务。RTOS 会自行创建一个任务,即空闲任务, 仅当没有其他任务能够执行时,该任务才会执行。RTOS 空闲任务总是处于 可以执行的状态。
请参阅上图:
起初,两个任务都不能运行:vControlTask 等待合适的时间来开始新的控制周期, 而 vKeyHandlerTask 则在等待按键操作。处理器时间分配给了 RTOS 空闲任务。
在时间 t1 处,发生按键事件。vKeyHandlerTask 可以执行,其优先级高于 RTOS 空闲任务, 因此获得了处理器时间。
在时间 t2 处,vKeyHandlerTask 已完成按键处理并更新 LCD。在按下另一个键之前该任务无法继续执行, 因此将自己挂起,RTOS 空闲任务恢复执行。
在时间 t3 处,定时器事件指示执行下一个控制循环的时间到了。vControlTask 现在可以执行, 因为优先级最高的任务被立刻分配了处理器时间。
在时间 t3 和 t4 之间,vControlTask 仍在执行时,发生了按键事件。vKeyHandlerTask 可以执行, 但由于其优先级低于 vControlTask,因此未获得任何处理器时间。
在 t4 处, vControlTask 完成了控制周期的处理,并且直到下一次定时事件的发生前不能重新开始运行, 进入阻塞态。vKeyHandlerTask 现在成为可以运行的最高优先级的任务, 因此获得处理器时间以处理先前的按键事件。
在 t5 处,按键事件处理完成,并且 vKeyHandlerTask 进入阻塞态等待下一次按键事件。再一次, 两个任务都未进入就绪态,RTOS 空闲任务获得处理器时间。
在 t5 与 t6 之间,定时事件发生并处理,没有进一步的按键事件发生。
在 t6 处发生按键事件,但在 vKeyHandlerTask 完成按键处理之前,发生了定时事件。 此时两个任务都可以执行。由于 vControlTask 具有更高的优先级, 因此 vKeyHandlerTask 在完成按键操作之前被挂起,vControlTask 获得处理器时间。
在 t8 处,vControlTask 完成控制周期的处理,然后进入阻塞态等待下一次事件。vKeyHandlerTask 再次 成为运行的最高优先级任务,因此获得处理器时间,以便完成按键处理 。
这里值得一提的是,当最高优先级定时事件到来时,正在执行的事件会被抢占,而当完成了控制周期的处理,并且直到下一次定时事件的发生前不能重新开始运行,进入阻塞态时,会根据优先级继续分配任务。就像落入荒野时,吃喝拉撒成为第一重要的事一样,其他的恩怨情仇都放在一边,当回归都市时,恩怨情仇又占据了日常。