本帖最后由 1308365377 于 2022-10-8 10:53 编辑
现在FreeRTOS做为大规模使用的实时操作系统,因为其开源,结构完整简单的优点被大量运用于物联网,工业检测与控制等领域。
现在我们就CW32L083的FreeRTOS做简单的介绍。
首先我们可以从官网下载最新的FreeRTOS的资料,FreeRTOS的官方网站为https://www.freertos.org/
Freetos book文件夹是官方的参考文档
FreeRTOS文件夹是官方提供的代码资源,Plus版本是在FreeRTOS的基础上增加了一些功能,这里我们就FreeRTOS为例进行移植。
Demo是FreeRTOS官方提供的一些不同内核的芯片例程,而我们的重点在于Source这个文件夹,这里包含着FreeRTOS的内核代码。
将这个文件夹整体复制到你建立的例程下,如在CW32L083的GPIO_blink这个例程下新建了一个FreeRTOS的文件夹,把刚刚复制的Source放在这个文件夹下。
然后打开Source这个文件夹,下面的C文件就是FreeRTOS的源码,include文件夹中的是FreeRTOS的头文件,接下来打开portable文件夹
Portable文件夹下是不同编译软件所需要的资源,由于本例程是在keil下运行的,所以除了KEIL,MenMang和RVDS这三个文件,其他的文件都删除,MemMang文件中存放的是5种内存管理的方式,RVDS文件夹下存放的是不同的ARM架构的内核。
除此之外,我们还需要一个重要文件,FreeRTOSConfig.h,这个文件是可以通过配置一些宏定义来对我们的实时系统进行一个裁剪,那么这个头文件在哪呢,可以在FreeRTOS发布的例程Demo中找到,然后将这个头文件复制到我们的例程中来就行。
然后打开CW32L083的例程,将FreeRTOS的资源加入到例程中来。
主要的程序代码如下:
#include "main.h"
#include "cw32l083_flash.h"
#include <stdio.h>
#include "FreeRTOS.h"
#include "task.h"
#include "cw32l083_gpio.h"
#include "cw32l083_rcc.h"
#include "task.h"
//#include "usart.h"
#define led1_tog() PC02_TOG()
#define led2_tog() PC03_TOG()
TaskHandle_t StartTask_Handler;
TaskHandle_t LedTask_Handler;
void start_task(void *pvParameters)
{
while(1)
{
led1_tog();
vTaskDelay(1000);
}
}
void led_task(void *pvParameters)
{
while(1)
{
led2_tog();
vTaskDelay(500);
}
}
void rcc_config(void)
{
uint8_t res =0U;
RCC_AHBPeriphClk_Enable(RCC_AHB_PERIPH_FLASH,ENABLE);
//RCC_HCLK_OUT();
//通过PA04观察HCLK频率
RCC_HSI_Enable( RCC_HSIOSC_DIV6 ); //设置HSI = HSIOSC/6
//开启HSI
RCC_PLL_Enable( RCC_PLLSOURCE_HSI, 8000000, RCC_PLL_MUL_8 ); //开启PLL,PLL源为HSI
FLASH_SetLatency(FLASH_Latency_3); //频率大于48M需要配置FlashWait=3,
res = RCC_SysClk_Switch( RCC_SYSCLKSRC_PLL ); //切换系统时钟到PLL
if( res == 0x00 ) //切换系统时钟成功
{
PC02_SETHIGH();
PC03_SETHIGH();
FirmwareDelay( 600000 );
}
else
{
while(1)
{
PC03_TOG();
PC02_TOG();
FirmwareDelay( 10000000 );
}
}
RCC_SystemCoreClockUpdate(64000000);
}
int32_t main(void)
{
rcc_config();
// uart_init(115200);
GPIO_InitTypeDef GPIO_InitStruct = {0};
__RCC_GPIOC_CLK_ENABLE();
GPIO_InitStruct.IT = GPIO_IT_NONE;
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStruct.Pins = GPIO_PIN_2 | GPIO_PIN_3;
GPIO_Init(CW_GPIOC, &GPIO_InitStruct);
xTaskCreate((TaskFunction_t)start_task,
(const char* )"start_task",
(uint16_t )128,
(void* )NULL,
(UBaseType_t )1,
(TaskHandle_t* )&StartTask_Handler);
xTaskCreate((TaskFunction_t)led_task,
(const char* )"led_task",
(uint16_t )128,
(void* )NULL,
(UBaseType_t )2,
(TaskHandle_t* )&LedTask_Handler);
vTaskStartScheduler(); //开启任务调度
}
除此之外我们还需要将上文中提到的FreeRTOSConfig.h的一些宏定义更改一下,下述的两个宏定义一个是CPU的时钟频率,因为我们主程序的时钟频率设置的 为64Mhz的时钟,所以在FreeRTOSConfig.h这个文件中将时钟频率改为64Mhz,然后因为我们使用了动态内存管理,所以我们需要设置堆的大小。具体修改如下图所示
在具体的编译之后,没有错误,下载到开发板上,LED1以1S改变一次状态,LED2灯500ms改变一次状态。
|