1 前言
最近在了解TencentOS的特性,据了解它的一些特点:
资源占用极少
高效功耗管理框架
自动移植工具
最后一屏调试工具
安全分级方案
它的官网这里:https://cloud.tencent.com/product/tos-tiny
正好我手上有极海家的APM32F407IGMINI板卡,我便计划基于这块板卡移植TencentOS来看看。
本文将记录移植的过程,也请各位大神多多斧正。
2 APM32F4 源码准备
我们去极海官网下载APM32F4的SDK包:
https://geehy.com/uploads/tool/APM32F4xx_SDK_V1.4.zip
打开SDK包我们找一个“顺眼的”demo作为我们的基础,以移植TencentOS,对就是你了“SysTick”例程。
本次我计划在MDK上实现APM32F4的TencentOS适配,所以我将选择“SysTick”例程的MDK工程。为了不和原工程混淆,我把“SysTick_TimeBase”复制至\Examples\RTOS目录下:
把“SysTick_TimeBase”名字改为“TencentOS”。
3 TencentOS源码获取
我们去TencentOS的Github仓库下载其最新的源码:
https://github.com/OpenAtomFoundation/TencentOS-tiny
关于TencentOS的源码我们比较关系的重要内容有:
由于我手上的APM32F4 尚未被TencentOS支持,所以我们在“board”文件夹中未能找到我们需要的东西,但可做参考。
本次考虑的是能够使得APM32F407正常运行TencentOS,所以我们更关心的是TencentOS tiny 适配的 IP 核架构、TencentOS tiny 内核源码这两部分的内容。
下面我们复将TencentOS源码复制或解压至“APM32F4xx_SDK_V1.4\Middlewares”文件夹中。
至此我们完成了源码的获取工作,接下来我们将进入MDK的工程设置进行一步步的把TencentOS移植。
4 移植TencentOS至APM32F407
打开我们刚刚在第2节中准备的工程:
我们将在该工程上进行修改。
4.1 TencentOS 源文件包含
首先我们先创建用于保存TencentOS的文件目录结构:
分别是:
TencentOS/arch
用于存放arch平台代码。
TencentOS/kemel
用于存放TencentOS内核源码,
TencentOS/cmsis_os
用于存放cmsis os 源码,
4.2 TencentOS 头文件路径包含
完成源文件包含后我们将所需的头文件包含进我们的工程。
4.3 复制tos_config.h
我们将和APM32F4 相同架构的STM32L431demo下的tos_config.h(APM32F4xx_SDK_V1.4\Middlewares\TencentOS-tiny\board\BearPi_STM32L431RC\TOS-CONFIG)文件复制到我们的目录下:
4.4 修改源码
4.4.1 修改tos_config.h的头文件包含为“apm32f4xx.h”
4.4.2 注释PendSV_Handler
注释掉apm32f4xx_int.c里面的PendSV_Handler函数,该函数将由TencentOS接管。
4.4.3 修改SysTick_Handler
TencentOS 需要SysTick做为时基,在“apm32f4xx_int.c”的头部增加“tos_k.h”引用。
然后修改SysTick_Handler函数如下:
`void SysTick_Handler(void)
{
// TimingDelay_Decrement();
if (tos_knl_is_running())
{
tos_knl_irq_enter();
tos_tick_handler();
tos_knl_irq_leave();
}
}`
4.4.4 修改main.c
在 main.c 中添加TencentOS tiny 头文件,编写任务函数:
任务函数编写可以参考官方提供的demo:
`//task1
#define TASK1_STK_SIZE 256
void task1(void *pdata);
osThreadDef(task1, osPriorityNormal, 1, TASK1_STK_SIZE);
//task2
#define TASK2_STK_SIZE 256
void task2(void *pdata);
osThreadDef(task2, osPriorityNormal, 1, TASK2_STK_SIZE);
void task1(void *pdata)
{
int count = 1;
while (1)
{
printf(“\r\nHello world!\r\n##
#This is task1 ,count is %d \r\n”, count++);
APM_MINI_LEDToggle(LED2);
osDelay(2000);
}
}
void task2(void *pdata)
{
int count = 1;
while (1)
{
printf(“\r\nHello TencentOS !\r\n***This is task2 ,count is %d \r\n”, count++);
APM_MINI_LEDToggle(LED3);
osDelay(1000);
}
}`
然后将main函数修改如下:
`int main(void)
{
USART_Config_T usartConfigStruct;
usartConfigStruct.baudRate = 115200;
usartConfigStruct.hardwareFlow = USART_HARDWARE_FLOW_NONE;
usartConfigStruct.mode = USART_MODE_TX;
usartConfigStruct.parity = USART_PARITY_NONE;
usartConfigStruct.stopBits = USART_STOP_BIT_1;
usartConfigStruct.wordLength = USART_WORD_LEN_8B;
APM_MINI_COMInit(COM1, &usartConfigStruct);
APM_MINI_LEDInit(LED2);
APM_MINI_LEDInit(LED3);
osKernelInitialize();//TOS Tiny kernel initialize
osThreadCreate (osThread(task1),NULL);//Create task1
osThreadCreate(osThread(task2),NULL);//Create task2
osKernelStart ();//Start Tos Tiny
while (1)
{
}
}
`
至此我们完成了代码的编写工作。
5 编译下载
完成代码的编写工作后,我们编译工程:
进行下载(我使用的是jlink)。然后使用串口线连接MINI板,打开串口助手可以看到两个任务可以正常打印,LED按照各自的延时时间正常闪烁。
至此,基于APM32F4的TencentOS 适配工作完成。你也来试试看吧。