FreeRTOS
移植和配置
- 移植
- 路径
- 配置
- 函数前缀字母与输出形式有关
- x 句柄
- v void
任务
- 创建
xTaskCreate(func, name, ram, param, priority, handle)
vTaskStartScheduler(void)
- 删除
vTaskDelete(handle)
NULL 可以删除自己 - 挂起
vTaskSuspend(handle)
vTaskResume(handle)
vTaskSuspendFromISR(handle)
vTaskSuspendAll(void)
vTaskResumeAll(void)
- 切换
taskYIELD(void)
- 调度
- 运行 就绪 阻塞 挂起
- 时间片调度 优先级调度
- 空闲任务 空闲任务回调函数 常用于进入低功耗模式
- 信息
vTaskList(buffer)
vTaskGetRunTimeStats(buffer)
- 优先级
vTaskPrioritySet(handle, newPriority)
uxTaskPriorityGet(handle)
- 临界区
- 临界区代码不会被中断打断,会影响系统的实时性, 常用于全局变量的保护和修改
taskENTER_CRITICAL(void)
taskEXIT_CRITICAL(void)
taskENTER_CRITICAL_FROM_ISR(void)
taskEXIT_CRITICAL_FROM_ISR(void)
taskDISABLE_INTERRUPTS(void)
在临界区开启中断 一般用退出
时间
- 轮转
vApplicationTickHook(void)
启用时间片轮转回调函数
- 延时
xTaskGetTickCount(void)
获取节拍赫兹xTaskGetTickCountFromISR(void)
中断中获取节拍赫兹vTaskDelay(ticks)
相对延时vTaskDelayUntil(p, ticks)
绝对延时vApplicationIdleHook(void)
启用空闲任务回调函数
任务栈
- 内存分配失败
vApplicationMallocFailedHook(void)
分配失败回调函数 - 溢出
vApplicationStackOverflowHook(handle,name)
栈溢出回调函数 - 确定大小
uxTaskGetStackHighWaterMark(handle)
返回最小剩余空间
内存管理
- 申请和释放
* pvPortMalloc(size)
申请空间vPortFree(pv)
释放vPortInitialiseBlocks(void)
初始化内存堆函数xPortGetFreeHeapSize(void)
未分配大小xPortGetMinimumEverFreeHeapSize(void)
最小未分配大小
- 动态分配
\Sourse\portable\MemMang\heap_x.c
内存管理方案- heap1: 分配后不允许释放
- heap2:可以释放但不合并,会造成碎片
- heap3:封装了malloc free 线程安全(多任务调用),占用大
- heap4: 支持内存碎片处理
- heap5: 支持将动态内存设置在不连续的区域上
通信
- 消息队列
xQueueCreate(length, size)
创建XQueueCreateStatic
静态xQueueSend(queue, p, waitTime)
xQueueSendFromISR(q, p, woken)
发到队尾xQueueSendToBack(q, p, wait)
基本同上xQueueSendToFront(q, p, wait)
发到队首xQueueReceive(q, buffer, wait)
获取xQueueReceiveFromISR(q, buffer, woken)
- 二值信号量
xSemaphoreCreateBinary(void)
创建xSemaphoreGive(sem)
xSemaphoreGiveFromISR(sem, woken)
给出xSemaphoreTake(sem, wait)
获取
- 计数信号量
xSemaphoreCreateCounting(maxNum, initNum)
- 互斥信号量
xSemaphoreCreateMutex(void)
- 优先级继承
- 递归信号量
xSemaphoreCreateRecursiveMutex(void)
xSemaphoreTakeRecursive(mutex, wait)
获取xSemphoreGiveRecursive(mutex)
释放
- 通知
- 每个任务的任务控制块都有一个32位的
ulNotifiedValue
变量 - 可以用于实现消息队列、信号量、事件组,速度更快
- 但缺陷在于,要求只要一个任务在等待,发送消息不支持超时等待
- 信号量
ulTaskNotifyTake(减少pdFALSE/清零pdTRUE,wait)
xTaskNotifyGive(handle)
xTaskNotifyGiveFromISR(handle, woken)
xTaskNotifyWait(输入前清除,退出前清除,pv, wait)
xTaskNotify(handle, value, mode)
xTaskNotifyFromISR(handle, value, mode, woken)
eNoAction
不改值eSetBits
改字节值eIncrement
加一eSetValueWithOverwrite
覆盖eSetValWithoutOverwrite
没收到就不改
- 每个任务的任务控制块都有一个32位的
- 事件组
xEventGroupCreate(void)
创建xEventGroupSetBits(group, bits)
xEventGroupSetBitsFromISR(group, bits, woken)
设置xEventGroupWaitBits(group, needBits, 退出清除,是否等待全部置一, wait)
定时器
- 定时器
xTimerCreate(name, period, reload, id, callback)
创建xTimerStart(timer, block)
启动pvTimerGetTimerID(timer)
获取id
- 低功耗
- 睡眠模式 WFE WFI
- 停机模式
PWR_EnterSTOPMode
- 待机模式
PWR_EnterSTANDBYMode
__HAL_RCC_PWR_CLK_ENABLE()
使能PWR 时钟__HAL_PWR_CLEAR_FLAG(PWR_FLAG_WU)
清除 Wake_UP 标志HAL_PWR_EnableWakeUpPin(PWR_WAKEUP_PIN1)
设置 WKUP 用于唤醒HAL_PWR_EnterSTANDBYMode()
进人待机模式
- tickless
- 空闲任务运行,其他任务挂起或阻塞,PECTED_IDIE_TIME_BEFORE_SLEEP小于低功耗模式节拍数时
- 系统自动调用
portSUPPRESS_TICKS_AND_SLEEP()
函数 进入低功耗模式
命令行
- CLI 移植 略
- CLI 命令
func(buffer, len, cmd)
实现命令FreeRTOS_CLIGetParameter(str, param, len)
命令参数 放在上面函数内FreeRTOS_CLIRegisterCommand(register)
注册命令FreeRTOS_CLIProcessCommand(input, buffer, len)
命令处理
文件
- FAT移植 略
I2C_Soft_Init()
初始化iic__HAL_RCC_CRC_CLK_ENABLE()
开启CRC时钟FF_SDDiskInit("/")
初始化sd卡
- 创建
ff_mkdir(dir)
创建文件夹ff_chdir(dir)
切换目录ff_rmdir(dir)
删除ff_getcwd(buffer, len)
查看当前工作目录
- 读写
ff_stdio.h
file = ff_fopen(filename, mode)
可以用于创建ff_fclose(file)
ff_fwrite(buffer, size, len, file)
ff_fread(buffer, size, len, file)
ff_fputc(char, file)
写入单字节ff_fgets(buffer, size,file)
读取字符串ff_fprintf(file, format)
格式化写入文件ff_fseek(file, offset, whence)
将读写位置移动到offset+whence
ff_ftell(file)
当前位置ff_seteof(file)
截断到当前位置ff_truncate(filename, maxsize)
打开文件,截断到最大长度ff_rewind(file)
回到开头
- 文件操作
ff_feof(file)
指针是否在文件末尾ff_rename(oldName, newName, 是否删除源文件)
移动或重命名ff_remove(path)
删除文件ff_stat(filename, buffer)
读取文件属性保存到bufferff_filelength(file)
文件长度ff_findfirst(dir, data)
目录中第一个文件ff_findnext(dada)
目录中下一个文件(夹)
网络编程
- TCP/IP 移植 略
- UDP
socket = FreeRTOS_socket(FREERTOS_AF_INET, FREERTOS_SOCK_DGRAM/STREAM, FREERTOS_IPPROTO_UDP/TCP)
创建FreeRTOS_setsocket(socket, level, option, value, len)
选项设置FreeRTOS_sendto(socket, buffer, len, flag, address, addrlen)
发送FreeRTOS_recvfrom(socket, buffer, len, flag, addr, addrlen)
接收
- TCP 客户端
FreeRTOS_connect(socket, addr, addrlen)
连接FreeRTOS_shutdown(socket, FreeRTOS_CLOST_RDWR)
关闭连接FreeRTOS_closesocket(socket)
关闭套接字FreeRTOS_send(socket, buffer, len, flags)
在上文连接后发送FreeRTOS_recv(socket, buffer, len, flags)
接收数据
- TCP 服务端
FreeRTOS_bind(socket, addr, addrlen)
绑定到本地端口号FreeRTOS_listen(socket, maxLink)
开始监听FreeRTOS_accept(socket, addr, addrlen)
接收连接