zoukankan      html  css  js  c++  java
  • FreeRTOS应用开发笔记之一:FreeRTOS在STM32的移植

      FreeRTOS是如今在小型嵌入式领域应用比较广泛的一种实时操作系统。它是一种开源且免费的操作系统,而且移植和使用都非常的简单。在这里我们将学习并移植FreeRTOS。

    1、必要的准备

      工欲善其事,必先利其器,在开始学习和移植之前,相应的准备工作必不可少。所以在开始我们需要有必要的准备:

    • 下载FreeRTOS源码,可以从官网下载源码,最新版本为V10.0.1,官网地址:https://www.freertos.org/a00104.html
    • 下载学习资料,FreeRTOS官方提供入门手册和参考手册,可以在线查看,也可以下载pdf版本的电子书。下载网址:https://www.freertos.org/Documentation/RTOS_book.html
    • 准备实验平台,此次我们将在STM32F407平台上移植和测试FreeRTOS系统

      下载的FreeRTOS源码是一个自解压的文件,解压后包含的内容比较丰富,不过目录结构很清晰,主要包含两个子目录:FreeRTOS和FreeRTOS-Plus。如下所示:

    • FreeRTOS-Plus       包含FreeRTOS+组件和演示例程;
    • FreeRTOS                包含FreeRTOS实时内核源文件和演示例程。

     

      我们学习的FreeRTOS内核部分在FreeRTOS目录之下,打开FreeRTOS文件夹它又被分成两个主要的子目录,如下所示:

    • Demo         包含演示例程工程;
    • License      包含授权文件
    • Source       包含实时内核源文件。

     

      RTOS代码的核心包含在三个文件中:tasks.c、queue.c、list.c。这三个文件位于FreeRTOS/Source目录。在该目录下还包含三个可选的文件:timers.c、event_groups.c、croutine.c,分别实现软件定时、事件组和协程功能。打开Source文件夹,FreeRTOS/Source目录结构如下所示:

     

      应用平台的不同,所以每个支持的处理器架构都有一段与处理器架构相关的RTOS代码。这个是RTOS移植层,它位于FreeRTOS/Source/Portable/[相应编译器]/[相应CPU架构]子目录。

      对于FreeRTOS,堆栈设计也属于移植层。FreeRTOS/Source/portable/MemMang目录下heap_x.c文件给出了多种堆栈方案,在后续的移植中,会详细说明。

    2、简单的移植

      前面我们简要说明了移植的准备工作,接下来我们开始最主要的移植。本次移植我们将在IAR平台上进行,首先要创建一个IAR项目。我们在IAR下创建一个名为pfreertos的项目,并添加Application、Drivers和Middlewares几个组。并在Application下添加EWARM和User组;在Drivers下添加CMSIS和STM32F4xx_HAL_Driver组;在Middlewares下添加FreeRTOS组,具体如下:

     

      至于具体文件的物理路径并没有特别要求,但为了便于管理,我们强烈建议放到一起。并将相关的FreeRTOS源码拷贝到该项目目录下。

      将FreeRTOSv10.0.1FreeRTOSSource目录下的源文件及include文件夹复制到新建项目的文件夹中。

     

      将FreeRTOSv10.0.1FreeRTOSSourceportableIARARM_CM4F目录下的三个文件也复制到新建项目的文件夹。

     

      将FreeRTOSv10.0.1FreeRTOSSourceportableMemMang目录下的heap_4.c文件复制到新建项目的文件夹。

     

      将FreeRTOSv10.0.1FreeRTOSDemoCORTEX_M4F_STM32F407ZG-SK目录下的FreeRTOSConfig.h文件复制到新建项目的文件夹。

     

      同时将这下文件添加到我们前面创建的pfreertos项目中,其它如ST驱动及用户应用也添加到项目中。并将相关的引用目录添加到项目属性中。需要说一下的是在Assembler中的Preprocessor标签下添加也需要添加FreeRTOSConfig.h的引用路径,因为在汇编文件中有对FreeRTOSConfig.h文件的引用。

     

      在FreeRTOSConfig.h 配置文件中,有如下3个宏定义:

      #define vPortSVCHandler          SVC_Handler

      #define xPortPendSVHandler     PendSV_Handler

      #define xPortSysTickHandler     SysTick_Handler

      需要在stm32f4xx_it.c文件中,将对应的三个空的函数定义注释掉。至此,其实编译就已不会有错,移植工作已经完成。当然在有些其他的基础库也需要使用SysTick时,我们也可以在中断中调用xPortSysTickHandler()函数来实现我们的需求。

    3、移植测试

      前面我们已经移植了FreeRTOS,接下来我们创建多个任务测试一下它。

      在main.c文件中添加相应的代码,声明如下函数及代码(我计划4个任务):

     1 /***************************************************************************
     2 函数声明
     3 ***************************************************************************/
     4 static void vTask1(void *pvParameters);
     5 static void vTask2(void *pvParameters);
     6 static void vTask3(void *pvParameters);
     7 static void vTask4(void *pvParameters);
     8 static void AppTaskCreate (void);
     9 
    10 /***************************************************************************
    11 变量声明
    12 ***************************************************************************/
    13 static TaskHandle_t xHandleTask1 = NULL;
    14 static TaskHandle_t xHandleTask2 = NULL;
    15 static TaskHandle_t xHandleTask3 = NULL;
    16 static TaskHandle_t xHandleTask4 = NULL;

      任务创建函数如下:

    1 static void AppTaskCreate (void)
    2 {
    3   xTaskCreate( vTask1, "vTask1",512, NULL,1, &xHandleTask1);
    4   xTaskCreate( vTask2, "vTask2",512, NULL,1, &xHandleTask2);
    5   xTaskCreate( vTask3, "vTask3",512, NULL,1, &xHandleTask3);
    6   xTaskCreate( vTask4, "vTask4",512, NULL,1, &xHandleTask4);
    7 }

      主函数如下:

    1 int main(void)
    2 {
    3   /* 创建任务 */
    4   AppTaskCreate();
    5   /* 启动任务调度,开始执行任务 */
    6   vTaskStartScheduler();
    7 }

      编译无错误4个任务同时运行。移植初步测试成功。

    4、几点说明

      在FreeRTOS中定义了多种内存管理方式,对应的文件有5个,那么每个文件实现了什么?怎么选用呢?我们对于内存管理的几个文件的大致内容描述如下:

    • heap_1.c:这是所有实现中最简单的一个。一旦分配内存之后,它甚至不允许释放分配的内存。
    • heap_2.c:和heap_1不同,这个方案使用一个最佳匹配算法,它允许释放之前分配的内存块。它不会把相邻的空闲块合成一个更大的块,可能会造成内存碎片。
    • heap_3.c:简单的包装了标准库中的malloc()和free()函数,包装后的malloc()和free()函数具备线程保护。
    • heap_4.c:这个方案使用一个最佳匹配算法,但不像方案2那样。它会将相邻的空闲内存块合并成一个更大的块。
    • heap_5.c:这个方案同样实现了heap_4.c中的合并算法,并且允许堆栈跨越多个非连续的内存区。

      在前面说过FreeRTOSConfig.h 配置文件中,有如下3个宏定义。该宏定义避免了修改启动文件,但有一个地方需要注意一下。就是第3个宏定义“#define xPortSysTickHandler       SysTick_Handler”。如果采用的是ST的标准库没有问题,但如果采用的是HAL库,由于HAL库需要SysTick中断才能稳定运行,所以不能采用宏定义,而是在stm32f4xx_it.c文件中的SysTick中断响应函数中调用xPortSysTickHandler函数。

    欢迎关注:

  • 相关阅读:
    淘宝技术
    GridView使用
    仿QQ底部切换(Fragment + Radio)
    ViewPage+Fragment(仿微信切换带通知)
    PopupWindow --- 弹出底部窗体
    Activity--弹出底部窗口
    eclipse code style
    抽象类和接口
    java.lang.IllegalStateException: Not connected to server
    android真机 adb调试sqlite数据库
  • 原文地址:https://www.cnblogs.com/foxclever/p/13584449.html
Copyright © 2011-2022 走看看