历史上的今天
今天是:2025年07月26日(星期六)
2021年07月26日 | 移植uc/OS-III最新版到小熊派开发板(STM32L431)
2021-07-26 来源:eefocus
一、uc/OS全家桶
Micrium Software提供了 RTOS 解决方案系列,俗称ucos全家桶,其中最为出名的就是 ucOS-II 和ucOS-III,于 2016 年成为 Silicon Labs 的一部分。

https://github.com/SiliconLabs
玩全家桶之前,肯定要先把RTOS内核玩起来,关于选择ucos-II还是ucos-III是个老生长谈的问题,上图解决:
uc/OS-III系统分为了三个开源仓库,要分别拉取。
① uC-OS3:
git clone https://github.com/SiliconLabs/uC-OS3.git1.

② uC-CPU:
git clone https://github.com/SiliconLabs/uC-CPU.git1.

③ uC-LIB:
git clone https://github.com/SiliconLabs/uC-LIB.git1.

本文中使用的开发板为小熊派IoT开发板,主控为STM32L431RCT6:
本文使用的开发工具是MDK 5.30版本,编译器版本为ARMCC5。
移植之前使用STM32CubeMX生成一份裸机工程,保证可以使用printf在串口正常打印。
1. 复制ucos内核文件到工程中
这里我全都复制过来,后续可以将未添加到MDK中的文件删除。
在工程下新建 ucOS-III 文件夹,存放ucOS-III相关文件。
① 复制ucos内核文件夹过来:
② 复制uC-CPU和uC-LIB两个文件夹过来:
2.添加文件到MDK工程
① 添加 ucos-iii/ports 分组,添加 PortsARM-Cortex-MARMv7-M 目录下的os_cpu_c.c文件,以及该目录下ARM目录下的os_cpu_a.asm文件和 os_cpu_c.c文件:
② 添加 ucos-iii/source分组,添加Source文件夹下的所有c文件(除去__dbg_uCOS-III.c):
③ 添加uC-LIB分组,添加uC-LIB文件夹下的4个c文件:
④ 添加uC-CPU分组,添加uC-CPU下的相关文件,如图:
⑤ 添加 ucos-iii/config 分组,添加配置文件,如下:
lib_cfg.h:uC-LIBCfgTemplate
os_cfg.h:CfgTemplate
cpu_cfg.h:uC-CPUCfgTemplate
3. 添加头文件路径到工程中

① 修改 cpu_cfg.h,配置本工程所使用内核中CPU的NVIC优先级位数:
② 修改 os_cfg.h,关闭系统中 APP HOOKS 功能:
5. 处理中断
RTOS中内核得以运行需要两个中断:
在pendSV异常处理中进行任务切换
在systick异常处理中进行内核时钟处理
首先包含进来ucos的头文件,修改 stm32l4xx_it.c 文件,在头文件添加:
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include "os.h"
/* USER CODE END Includes */
① 处理pendSV异常,如下:
/**
* @brief This function handles Pendable request for system service.
*/
void PendSV_Handler(void)
{
/* USER CODE BEGIN PendSV_IRQn 0 */
OS_CPU_PendSVHandler();
/* USER CODE END PendSV_IRQn 0 */
/* USER CODE BEGIN PendSV_IRQn 1 */
/* USER CODE END PendSV_IRQn 1 */
}
② 处理Systick异常,如下:
/**
* @brief This function handles System tick timer.
*/
void SysTick_Handler(void)
{
/* USER CODE BEGIN SysTick_IRQn 0 */
/* USER CODE END SysTick_IRQn 0 */
HAL_IncTick();
/* USER CODE BEGIN SysTick_IRQn 1 */
OS_CPU_SysTickHandler();
/* USER CODE END SysTick_IRQn 1 */
}
至此,移植完成。
四、测试系统调度和延时
在main.c中按照如下过程编写测试代码。
① 引入ucos头文件:
/* Private includes ----------------------------------------------------------*/
/* USER CODE BEGIN Includes */
#include #include "os.h" /* USER CODE END Includes */ ② 定义任务栈、任务控制块、任务入口函数: /* Private variables ---------------------------------------------------------*/ /* USER CODE BEGIN PV */ static OS_TCB Task1TCB; static CPU_STK Task1Stk[512]; static void Task1_entry(void *p_arg) { OS_ERR err; (void)p_arg; while(1) { printf("task1 is running...rn"); OSTimeDly(1000, OS_OPT_TIME_DLY, &err); } } static OS_TCB Task2TCB; static CPU_STK Task2Stk[512]; static void Task2_entry(void *p_arg) { OS_ERR err; (void)p_arg; while(1) { printf("task2 is running...rn"); OSTimeDly(1000, OS_OPT_TIME_DLY, &err); } } /* USER CODE END PV */ ③ 在main函数中定义错误值变量: /* USER CODE BEGIN 1 */ OS_ERR err; /* USER CODE END 1 */ ④ 在main函数中初始化内核、创建两个任务、启动内核: /* USER CODE BEGIN 2 */ printf("uc/OS-III Port On BearPi Board By Mculover666rn"); /* 初始化 uc/OS 内核 */ OSInit(&err); /* 创建task1 */ OSTaskCreate((OS_TCB *)&Task1TCB, //任务控制块指针 (CPU_CHAR *)"Task 1", //任务名称 (OS_TASK_PTR )Task1_entry, //任务入口函数 (void *)NULL, //任务入口函数的参数 (OS_PRIO )2, //任务优先级 (CPU_STK *)&Task1Stk[0], //任务栈地址 (CPU_STK_SIZE )512 / 10, //任务栈监测区大小 (CPU_STK_SIZE )512, //任务栈大小 (OS_MSG_QTY )0, //任务支持接受的最大消息数 (OS_TICK )0, //时间片 */ (void *)0, //堆栈空间大小 (OS_OPT )(OS_OPT_TASK_STK_CHK | OS_OPT_TASK_STK_CLR), /* OS_OPT_TASK_STK_CHK 使能检测任务栈,统计任务栈已用的和未用的 OS_OPT_TASK_STK_CLR 在创建任务时,清零任务栈 */ (OS_ERR *)&err); /* 创建task2 */ OSTaskCreate((OS_TCB *)&Task2TCB, (CPU_CHAR *)"Task 2", (OS_TASK_PTR )Task2_entry, (void *)0, (OS_PRIO )3, (CPU_STK *)&Task2Stk[0], (CPU_STK_SIZE )512 / 10, (CPU_STK_SIZE )512, (OS_MSG_QTY )0, (OS_TICK )0, (void *)0, (OS_OPT )(OS_OPT_TASK_STK_CHK | OS_OPT_TASK_STK_CLR), (OS_ERR *)&err); /* 启动内核 */ OSStart(&err); (void)&err; /* USER CODE END 2 */ ⑤ 编译,下载,在串口助手中查看输出:
接下来就可以愉快的去玩uc/OS-III内核啦~还可以玩玩全家桶,go go go!
史海拾趣
|
file:///C:/Documents%20and%20Settings/Administrator.4797A7AA28774FE/桌面/未命名.bmp请问这个电路中电感RFC和电容Cbypass值应如何计算,假如放大器的输出频率为5000MHz… 查看全部问答> |
|
如谁有这方面的材料的 请发给我一下可以么?不一定符合下面的要就的,关于多点温度检测系统的都可以发给me,设计一个多点温度检测系统,系统结构框图如下 : 温度测点1→ → 检测器单元1   ...… 查看全部问答> |
|
VXWORKS启动时超级终端会打印以下信息: Copyright 1984-1998 Wind River Systems, Inc. CPU: Motorola ADS - PowerPC 860 VxWorks: 5.4 ...… 查看全部问答> |
|
在嵌入式系统上做Qt串口显示程序 ,make后出现的问题,查了一些资料,有的说是pro里面的HEADERS忘记加就会出现这个问题(具体加什么没说);有的说是出现“undefined reference”表示你缺少*.h 困扰很 ...… 查看全部问答> |
|
我现在写不了某些寄存器(就I2C寄存器写不进去,其他都可以) 有遇见这种问题的么? 我是关了MMU的啊~ 情况如下: 我在shell中输入 查看内存0x55000000位置的寄存器。 d 0x55000000 55000000: 0100 0000 0000 0000 0000 0000 00 ...… 查看全部问答> |
|
求购 S3C4510B 的开发板 最近找了份4510b的资料,看着不错可惜没有板子练。真是郁闷啊!不知道哪为高手还有收藏! 有的话留个言! 电话:13141280460 qq:406672875… 查看全部问答> |
|
在自测试模式下,想实现从邮箱1发数据给邮箱3,但是运行程序发现TRS寄存器不能置位,信息发不出去,不知道怎么回事。 有没有人遇到过类似情况呢? 程序如下 void InitECan(void) { struct ECAN_REGS ECanaShadow; EALLOW; / ...… 查看全部问答> |
|
学习C5416已经很久了,但是进度非常的慢,一个人盲打莽撞。 最近又碰上了个卡了很久的问题: 想用一个串口实现同时输入输出,因为C5416是全双工的。我用5416与TLV2541和TLV5636相接实现信号的输入与输出。 5416一个 ...… 查看全部问答> |
|
The embedded system of the analog design 好书适合数字工程师了解的模拟知识 本书为那些希望掌握基本模拟知识的数字工程师而写,内容包括A/D转换器、D/A转换器、运放、滤波器以及模拟和数字系统集成设计。 本书特别适合那些从事信息家电、工业控制和机电控制系统等模拟/数字 ...… 查看全部问答> |




