一、源码描述
1.头文件:freertos.h、FreeRTOSConfig.h
2.核心文件:
3.架构文件和内存管理文件
二、内存管理
在C语言的库函数中,有mallc、free等函数,但是在FreeRTOS中,它们不适用:
- 不适合用在资源紧缺的嵌入式系统中
- 这些函数的实现过于复杂、占据的代码空间太大
- 并非线程安全的(thread- safe)
- 运行有不确定性:每次调用这些函数时花费的时间可能都不相同
- 内存碎片化
- 使用不同的编译器时,需要进行复杂的配置
- 有时候难以调试
FreeRTOS在创建任务时,需要2个内核对象:task control block(TCB)、stack。
Heap_1
它只实现了pvPortMalloc,没有实现vPortFree。
它的实现原理很简单,首先定义一个大数组,然后,对于pvPortMalloc调用时,从这个数组中分配空间。
Heap_2
使用最佳匹配算法,支持vPortFree。
分配小能满足pvPortMalloc内存的空闲内存块。
最佳匹配算法:
- 假设heap有3块空闲内存:5字节、25字节、100字节
- pvPortMalloc想申请20字节
- 找出最小的、能满足pvPortMalloc的内存:25字节
- 把它划分为20字节、5字节
- 返回这20字节的地址
- 剩下的5字节仍然是空闲状态,留给后续的pvPortMalloc使用
与Heap_4相比,Heap_2不会合并相邻的空闲内存,所以Heap_2会导致严重的"碎片化"问题。
但是,如果申请、分配内存时大小总是相同的,这类场景下Heap_2没有碎片化的问题。所以它适合这种场景:频繁地创建、删除任务,但是任务的栈大小都是相同的(创建任务时,需要分配TCB和栈,TCB总是一样的)。
Heap_3
Heap_3使用标准C库里的malloc、free函数,所以堆大小由链接器的配置决定,配置项configTOTAL_HEAP_SIZE不再起作用。
C库里的malloc、free函数并非线程安全的,Heap_3中先暂停FreeRTOS的调度器,再去调用这些函数,使用这种方法实现了线程安全。
Heap_4
使用首次适应算法(first fit)来分配内存。它还会把相邻的空闲内存合并为一个更大的空闲内存,这有助于较少内存的碎片问题。
分配最先能满足pvPortMalloc内存的空闲内存。
首次适应算法:
- 假设堆中有3块空闲内存:5字节、200字节、100字节
- pvPortMalloc想申请20字节
- 找出第1个能满足pvPortMalloc的内存:200字节
- 把它划分为20字节、180字节
- 返回这20字节的地址
- 剩下的180字节仍然是空闲状态,留给后续的pvPortMalloc使用