S32K144 基于 MDK5 移植 FreeRTOS 10.1.1

关键字 :S32K144FreeRTOS

一、简介

文档主要是介绍如何将 FreeRTOS 10.1.1 版本移植到 S32K144 平台上,使用的 IDE 为 MDK5。文档主要包括了两个部分:FreeRTOS 移植 和 FreeRTOS 验证。

  • FreeRTOS 移植:在 FreeRTOS 官网获取到 OS 的源码,分析文件架构,通过提取里面需要的文件来完成移植;
  • FreeRTOS 验证:基于移植完成的 FreeRTOS基础上,编译没有错误前提下,再移植 LED Driver 到操作系统的工程上,验证系统运行的可行性;

在使用 OS 之前,我们首先要确保底层的 Driver 在裸机的情况下能正常运作,这样减少后期排查问题的难度,所以在获取完整的 FreeRTOS 源码后,中间会介绍一节基于裸机的开发的 LED Driver内容,最后 FreeRTOS 移植成功后, 再把 LED Driver 移植到上面去。这样一整个移植的工作流程就完成了。

二、FreeRTOS 源码的获取

  1. FreeRTOS 官方网站

https://www.freertos.org/

点击左边的【Download Source】,选择相应的方式下载源码:

 

【Latest News】显示的是当前 FreeRTOS 的版本信息和支持的一些芯片信息,点击【Download Source Code and Projects】后,稍等一会就会自动下载官方的 .exe 文件:FreeRTOSv10.1.1.exe,双击运行,选择安装目录,等待完成,目录结构如下:

① FreeRTOS : 主要存放的是 OS 的源码和 DEMO;

② FreeRTOS-Plus : 主要存放的是 OS 的一些扩展功能,比如 TCP/IP;

我们目前要使用的是 FreeRTOS 目录的内容:

① DEMO :FreeRTOS 给各个厂商开发的例程文件;

② License : 里面存放了 license 说明文档;

③ Source :  内核代码文件,移植主要用到的文件都在这里面;

 

① include : 存放的事通用的头文件

② portable : 与编译器有关的代码,里面存放着不同编译器的工程文件;

我们需要移植到 keil 上面,但是打开这个文件夹,里面只有一个 readme.txt,

提示直接看 RVDS,这时候我们需要的文件目录大概就是:

① Source 目录下的文件

② Source 目录下的 include 文件夹

③ Source 目录下的 portable 文件夹下面的MemMang 和 RVDS

④ Demo 目录下的例程里面的FreeRTOSConfig.h 文件

三、LED 裸板 Driver

  • S32K144 EVB Board

  • MDK 新建工程

打开 MDK ,新建工程:




① app 文件夹:存放 main.c 文件

② bsp 文件夹:存放底层驱动文件

③ doc 文件夹:存放文本说明文件

 










到这里,我们的工程新建和设置完成,需要注意的一点就是,S32K144.h 这个文件要把它放到工程里面,app 文件夹或者 bsp 文件夹,接下来就是裸板点亮小灯:

代码编译没有问题之后,把代码下载到 EVM 板子上,可以看到小灯间断的闪烁,说明这个裸板 Driver 是可以实现功能的,这就为下一步移植到 FreeRTOS 上打下了基础。

 

四、移植 FreeRTOS 及验证

裸板的 Driver 的工程已经完成,现在就把 FreeRTOS 移植过来,在工程目录新建文件夹:

① src : 把 FreeRTOS 目录下的源文件都放进来,除了 include 文件夹和 portable 文件夹

② include : 把 FreeRTOS 目录下的 include 文件夹复制过来

③ portable : 把 RVDS 文件夹和 Memmang 文件夹复制过来

 

在工程里面添加组,并把相应文件都添加进来:

① freertos/src :把所有 src 文件夹里面的源文件都添加进来

② freertos/portable : 把 MemMang 文件夹的 heap_4.c 和 RVDS/ ARM_CM4F/port.c 添加进来

③ app : 把Demo 里面的CORTEX_M4F_STM32F407ZG-SK 的FreeRTOSConfig.h 复制到 app 文件夹

把 main.c 头文件添加 FreeRTOS 系统的头文件,

先进行一次编译,发现报错:

从报错的内容看,都是缺少定义后缀为 Hook 的函数,这些函数都是钩子函数,我们在提示错误的源文件里面都能找到相应的函数声明:

因为我们在 FreeRTOSConfig.h 里面打开了一些宏定义,这些宏定义打开后,源文件会使用这些钩子函数,这里我们只要把这些钩子函数定义一下就行了,在 main.c 我们把这几个钩子函数都定义出来:


添加定义完成后,我们再次编译,

修改 FreeRTOSConfig.h

再次编译,发现编译已经能正常通过了:

至此,FreeRTOS 相应的文件已经都添加进来了,点击编译,能正常编译通过,但是系统还不能工作,因为 FreeRTOS 需要一个定时器作为系统的心跳,cortex-m4 内核提供了一个 systick 系统定时器,做为嵌入式操作系统的心跳,我们参考清华大学出版社出版的《ARM Cortex-M3与Cortex-M4权威指南》和 ARM 官方的文件《Cortex™-M4 Devices Generic User Guide》来配置 systick 定时器。

配置完 systick 定时器,只是开启了定时以及中断使能,但是中断优先级还没有设置,cortex-m4 内核有一个系统控制块单元 SBC,System Control Block 的 SHR 寄存器可以配置系统中断的优先级:

最终寄存器配置:

配置完 systick ,main.c 也需要修改,FreeRTOS 需要建立任务才能执行:

 

在主函数初始化 systick 后,利用 FreeRTOS 系统提供的接口 xTaskCreate 创建名字为 “App” 的任务,点击编译:

从提示中可以看到,错误提示的是 head_4.c 的 bss 段没有空间存放了,这时候看 FreeRTOSConfig.h 里面的配置:

堆栈目前设定的大小是 75*1024,太大了,设置小一点 :

这时候编译就通过了。把程序下载到 EVM 板子上,就可以看到蓝色的小灯不停的闪烁,这说明移植过来的 FreeRTOS 能工作了,到此, 整个移植流程已经完成了。

五、UART 驱动移植

前面已经成功移植了操作系统和 LED 驱动,现在基于上面的工程,添加 UART 驱动程序,实现与上位机的数据发送和接收功能。

  • UART 原理图

根据 EVM 板子的原理图,选择 PTC6 作为 UART1 的 RX,PTC7 作为 UART1 的 TX。EVM 板子通过下载的 USB 就可以实现通过 UART 功能,所以不需要另外的转换芯片。

  • 裸板软件配置

UART1 使用中断来接收数据,所以首先配置要使用的 TX、RX 引脚,然后需要配置 UART1 接收中断的使能位以及优先级,接着开启UART1 的外设时钟,配置 UART1 的波特率为 115200,1 位停止位,8 位数据格式,无奇偶校验位。


UART1 的基本配置已经完成了,但是开发程序的时候,一般会使用打印函数 printf,来作为一种调试信息的输出手段,现在需要实现 printf 函数的重定向,要不然无法使用 printf 输出信息。Printf 最终使用到函数fputc ,现在需要结合实际情况来填充这个fputc 函数:

在fputc 函数里面,等到发送位被置位的时候,需要把发送的数据放到 UART1 的发送寄存器中,这时候就可以完成发送。完成了函数填充后,还需要配置一下避免使用半主机模式:

这里面需要用到标准库的一些东西,需要包含标准库的头文件 #include 。配置后,使用的是标准库输入输出函数,不需要使用微库了,所以 MDK 的微库选项可以不勾选:

 

现在就可以使用 printf 函数实现打印信息功能了,接收部分还需要实现 UART1 中断函数:

程序完成后,使用串口工具测试一下通信。在“我的电脑”-> “管理”-> “设备管理器”里面查看串口号:

打开串口相关的工具,设置正确的波特率和数据格式属性:

经过测试,裸板的 UART1 的驱动没有问题,可以进行收发,接下来就可以把它移植到 FreeRTOS 上去。

  1. 移植到 FreeRTOS

把裸板的 uart.c 和 uart.h 复制到 FreeRTOS 工程目录的 BSP 文件夹下,名字分别改为 bsp_usrt.c 和 bsp_usrt.h,在 MDK 中把这两个文件添加进来:

为了方便管理,使用一个 bsp_config.c 来统一初始化底层驱动,bsp_config.c 要包含 bsp_usrt.h ,以便于下一步对 UART1 进行初始化。在 bsp_init 底层初始化函数里面把 UART1 的初始化添加进来:

底层初始化完了之后,在 FreeRTOS 基础上需要进行下面几步:

①定义接收数据类型,以便于接收完成后,使用队列向接收任务发送数据

② 申请队列

③ 建立接收任务

首先要定义一个用于接收的数据类型:

定义的类型里面包含了数据的:头部,长度,数据域,CRC检验。接着向 FreeRTOS 申请一个队列,队列深度为 1 ,大小为新定义的数据类型的大小:

这时候 main.c 要包含 FreeRTOS 的队列头文件 #include "queue.h",然后需要建立一个任务用来接收数据,任务的优先级位 2:

在接收函数里面,把当前系统运行的任务、任务的状态、堆栈使用情况等打印出来。由于现在定义了一个类型,所以裸板的驱动的中断接收函数需要修改一下,要把接收到的数据赋值给新定义的类型实例,然后再通过申请到的队列发送给接收任务:

在接收任务中,当接收到队列中的数据时,会把数据打印出来,通过上位机可以看到打印的信息。修改完后,编译通过,下载到 EVM 板子,复位后,可以看到蓝色的 LED 不停的闪烁,因为是基于上一节的工程做的移植,上一节已经把 LED 的驱动移植过来了,LED 任务的优先级为 4。这时候接上串口工具,并设置好相应的参数,然后就通过串口工具发送数据给下位机 — EVM 板:

通过上位机发送数据0xff 0x03 0x19 0x18 0x17 0x66,在接收任务中把数据头部去掉了,不打印,通过 下位机返回的看,发送过去的数据已经完全被接收到了。当前的任务状态也打印出来了,当前运行的任务一共有四个,用户建立的两个:APP 和 RX,系统任务有两个:IDLE 和 tmr Svc。到此,UART1 的移植测试完成了。

 


参考文献

《ARM Cortex-M3与Cortex-M4权威指南》

《CM3权威指南》

《Cortex™-M4 Devices Generic User Guide》

★博文内容均由个人提供,与平台无关,如有违法或侵权,请与网站管理员联系。

★文明上网,请理性发言。内容一周内被举报5次,发文人进小黑屋喔~

评论