1、将下载的rt-thread-2.0.1解压后,得到如下图所示的文件列表。

在bsp目录下可以找到stm32f40x文件夹,这文件夹里面包括了库函数,其他芯片平台的文件夹统统删掉。在libcpu下,只需要将arm文件夹里面的common和cortex-m4留下来,其他的也都统统删掉。还有其他一些辅助性的文件,如:documentation、examples、tools什么的我们也统统删掉,处理完这些后,一个干净的RTT就准备好了。

2、虽然RT-thread将文件分类的很好,但最好还是根据自己的项目习惯将整个项目整理一下。将整个软件项目分成四个部分:app,bsp,mdk,rt-thread-2.0.1。如下图所示。

app:应用层,存放项目开发时自己编写的应用文件

bsp:驱动层,里面主要包括了RT-thread在stm32f40x平台中的底层驱动(applications,drivers,libraries_1.5.0),以及项目所使用的外设驱动(peripheral)

mdk:存放keil mdk5.15的相关工程文件

rt-thread-2.0.1:系统层,存放rt-thread-2.0.1中的components(系统组件),include(系统内核头文件),libcpu(芯片移植)和src(系统内核源文件)

3、安装好keil mdk5.15后,新建项目工程文件并保存在mdk文件夹中。根据项目文件分类添加源文件,如下图所示。

然后向工程添加头文件目录,如下图所示。


4、配置stm32f407vgt6系统时钟

(1)在stm32f4xx.h文件中选择#define STM32F40_41xxx以及#define USE_STDPERIPH_DRIVER;

(2)修改stm32f4xx.h文件中默认的系统外部晶振时钟#define HSE_VALUE    ((uint32_t)8000000)

(3)修改system_stm32f4xx.c文件中所选器件有关系统时钟的PLL_M,PLL_N的值(PLL_P=2)。对于stm32f407xx,系统时钟为168MHZ,一般只需修改PLL_M,PLL_N。

#if defined(STM32F40_41xxx) || defined(STM32F427_437xx) || defined(STM32F429_439xx) || defined(STM32F401xx)
       /* PLL_VCO = (HSE_VALUE or HSI_VALUE / PLL_M) * PLL_N */
      #define PLL_M 8

......

#if defined(STM32F40_41xxx) || defined(STM32F427_437xx) || defined(STM32F429_439xx) || defined(STM32F446xx)
      #define PLL_N 336
      /* SYSCLK = PLL_VCO / PLL_P */

(4)使用stm32f40_41xxx的FPU,需要在SystemInit函数开头添加相关语句,同时在keil工程配置中Floating Point Hardware选择 "Use Single Precision" 。

(在stm32f4xx.h中已默认设置#define __FPU_PRESENT 1,在core_cm4.h中已默认设置__FPU_USED == 1)。

/* FPU settings ------------------------------------------------------------
      * If no this settings,it maybe enter HardFault_Handler() interrupt when mdk complier chose "Use Single Precision" to use FPU instruction. */
     #if (__FPU_PRESENT == 1) && (__FPU_USED == 1)
     SCB->CPACR |= ((3UL << 10*2)|(3UL << 11*2)); /* set CP10 and CP11 Full Access */
     #endif

(5)在stm32f4xx_it.h和stm32f4xx_it.c中将HardFault_Handler,PendSV_Handler以及SysTick_Handler三个中断入口函数注释掉。

HardFault_Handler,PendSV_Handler在context_rvds.S文件中分别实现RT-thread系统异常处理和线程切换;

SysTick_Handler在board.c中实现RT-thread系统时钟节拍计数。

(6)在board.h中确定stm32f407的SRAM大小,以及SRAM结束地址。stm32f407vg共有192K的SRAM(其中可被访问的只有128k,起始地址为0x20000000)。

// <o> Internal SRAM memory size[Kbytes] <8-64>
       // <i>Default: 64
      #define STM32_SRAM_SIZE 128
      #define STM32_SRAM_END (0x20000000 + STM32_SRAM_SIZE * 1024)

5、若需要在项目中启用finsh组件以及组件初始化函数,为了保证用户自行编写的函数不会被keil编译器优化掉,则需要修改MDK设置,如下:

在Linker->Misc controls标签下,键入”--keep __fsym_* --keep __vsym_* --keep __rt_init_*”这个命令,该命令会保留未被函数主体调用的函数。这样在使用finsh组件调试时仍然可以运行没有被调用过的函数。

6、修改系统配置文件rtconfig.h的相关系统参数,如下面所示为系统基础配置:

/* RT-Thread config file */
#ifndef __RTTHREAD_CFG_H__
#define __RTTHREAD_CFG_H__ /* RT_NAME_MAX*///指定了系统内核对象名称的最大长度(比如线程,信号量,互斥锁,事件等),多余部分会自动裁掉
#define RT_NAME_MAX 8 /* RT_ALIGN_SIZE*///大多数系统需要对栈空间地址对齐(例如ARM体系结构中需要向4字节地址对齐),系统默认设置为4字节对齐,这里可设置以8字节对齐
#define RT_ALIGN_SIZE 8 /* PRIORITY_MAX *///RT-thread最大可支持256个线程优先级(0~255,0为最高优先级,255分配给空闲线程)。在资源有限情况下,一般设置为最大支持8个或32个优先级。
#define RT_THREAD_PRIORITY_MAX 32 /* Tick per Second *///系统时钟每秒节拍数,1000表示1s内rt_tick增加1000,即时钟节拍为1ms;若设为100,则rt_tick每隔10ms加1,时钟节拍为10ms。
#define RT_TICK_PER_SECOND 1000 /* Using Hook *///使用钩子(回调)函数
#define RT_USING_HOOK /* Idle thread stack *///设置空闲线程的栈空间大小为1024字节
#define IDLE_THREAD_STACK_SIZE 1024 /* Using Software Timer *///软件定时器线程模式(这里不采用该模式)。RT-thread系统时钟一般默认采用所选芯片平台的硬件定时器中断模式
// #define RT_USING_TIMER_SOFT
#define RT_TIMER_THREAD_PRIO 4
#define RT_TIMER_THREAD_STACK_SIZE 512 /* SECTION: RT_DEBUG *///线程调试以及组件初始化模块
/* Thread Debug */
#define RT_DEBUG
#define RT_DEBUG_INIT 1 //组件初始化调试模式(若不需要通过串口控制台向PC端打印初始化信息,则没有必要启用该模式)
#define RT_USING_COMPONENTS_INIT //启用组件初始化功能
#define RT_USING_OVERFLOW_CHECK //启用线程栈溢出检查 /* SECTION: IPC *///进程间通信内核对象:信号量,互斥锁,事件,邮箱,消息队列
/* Using Semaphore*/
#define RT_USING_SEMAPHORE
/* Using Mutex */
#define RT_USING_MUTEX
/* Using Event */
#define RT_USING_EVENT
/* Using MailBox */
#define RT_USING_MAILBOX
/* Using Message Queue */
#define RT_USING_MESSAGEQUEUE /* SECTION: Memory Management *///RT-thread系统内存管理:使用静态内存池,动态堆(小内存管理算法)
/* Using Memory Pool Management*/
#define RT_USING_MEMPOOL
/* Using Dynamic Heap Management */
#define RT_USING_HEAP
/* Using Small MM */
#define RT_USING_SMALL_MEM /* SECTION: Device System *///系统组件之I/O设备管理:启用I/O设备以及设备间通信
/* Using Device System */
#define RT_USING_DEVICE //根据rtdevice.h中所有设备的宏定义,在rtconfig.h中打开相应宏定义,如以下4类设备
/* Using GPIO pin framework *///GPIO设备
#define RT_USING_PIN
/* Using serial framework */ //串口设备
#define RT_USING_SERIAL
/* Using SPI framework */ //SPI设备
#define RT_USING_SPI
/* Using I2C framework */ //I2C设备
#define RT_USING_I2C
#define RT_USING_I2C_BITOPS /* SECTION: Console options *///系统控制台:启用控制台以及设置控制台设备缓存256字节。若使用rt_kprintf向PC端打印信息,则必须启用控制台并设置控制台设备(如串口)。
#define RT_USING_CONSOLE
/* the buffer size of console*/
#define RT_CONSOLEBUF_SIZE 256 /* SECTION: finsh, a C-Express shell *///finsh组件(finsh是RT-thread系统的命令行外壳,提供一套供用户在命令行的接口,主要用于调试,查看系统信息)
#define RT_USING_FINSH
/* Using symbol table */
#define FINSH_USING_SYMTAB
#define FINSH_USING_DESCRIPTION /* SECTION: device filesystem *///文件系统
/* Using Device file system */ //在项目中没有使用文件系统
// #define RT_USING_DFS
/* the max number of mounted filesystem */
#define DFS_FILESYSTEMS_MAX 2
/* the max number of opened files */
#define DFS_FD_MAX 4 /* Using ELM FATFS *///ELM FATFS文件系统(在项目中没有使用)
// #define RT_USING_DFS_ELMFAT
#define RT_DFS_ELM_WORD_ACCESS
/* Reentrancy (thread safe) of the FatFs module. */
#define RT_DFS_ELM_REENTRANT
/* Number of volumes (logical drives) to be used. Each volumes maybe include one primaly partition and some logical partitions.
* If _MULTI_PARTITION is defined to 0 in ffconf.h, each volume can mount only first primaly partition */
#define RT_DFS_ELM_DRIVES 2
/* Long File Name(LFN) with dynamic LFN working buffer on the heap. */
#define RT_DFS_ELM_USE_LFN 3
#define RT_DFS_ELM_MAX_LFN 255
/* The _CODE_PAGE specifies the OEM code page to be used on the target system. 936-Simplified Chinese GBK (DBCS, OEM, Windows); 437 - U.S.(OEM) */
#define RT_DFS_ELM_CODE_PAGE 437
/* Maximum sector size to be handled. It must be the real size(byte) of spiflash sectors. */
#define RT_DFS_ELM_MAX_SECTOR_SIZE 4096 /* Using ROM file system *///ROMFS文件系统(在项目中没有使用)
// #define RT_USING_DFS_ROMFS /* SECTION: lwip, a lighwight TCP/IP protocol stack *///轻型TCP/IP协议栈(在项目中没有使用)
// #define RT_USING_LWIP
/* LwIP uses RT-Thread Memory Management */
#define RT_LWIP_USING_RT_MEM
/* Enable ICMP protocol*/
#define RT_LWIP_ICMP
/* Enable UDP protocol*/
#define RT_LWIP_UDP
/* Enable TCP protocol*/
#define RT_LWIP_TCP
/* Enable DNS */
#define RT_LWIP_DNS /* the number of simulatenously active TCP connections*/
#define RT_LWIP_TCP_PCB_NUM 5 /* ip address of target*/
#define RT_LWIP_IPADDR0 192
#define RT_LWIP_IPADDR1 168
#define RT_LWIP_IPADDR2 1
#define RT_LWIP_IPADDR3 201 /* gateway address of target*/
#define RT_LWIP_GWADDR0 192
#define RT_LWIP_GWADDR1 168
#define RT_LWIP_GWADDR2 1
#define RT_LWIP_GWADDR3 1 /* mask address of target*/
#define RT_LWIP_MSKADDR0 255
#define RT_LWIP_MSKADDR1 255
#define RT_LWIP_MSKADDR2 255
#define RT_LWIP_MSKADDR3 0 /* tcp thread options */
#define RT_LWIP_TCPTHREAD_PRIORITY 12
#define RT_LWIP_TCPTHREAD_MBOX_SIZE 4
#define RT_LWIP_TCPTHREAD_STACKSIZE 1024 /* ethernet if thread options */
#define RT_LWIP_ETHTHREAD_PRIORITY 15
#define RT_LWIP_ETHTHREAD_MBOX_SIZE 4
#define RT_LWIP_ETHTHREAD_STACKSIZE 512 /* TCP sender buffer space */
#define RT_LWIP_TCP_SND_BUF 8192
/* TCP receive window. */
#define RT_LWIP_TCP_WND 8192 #define CHECKSUM_CHECK_TCP 0
#define CHECKSUM_CHECK_IP 0
#define CHECKSUM_CHECK_UDP 0 #define CHECKSUM_GEN_TCP 0
#define CHECKSUM_GEN_IP 0
#define CHECKSUM_GEN_UDP 0 /* RT_GDB_STUB *///GDB调试工具(在项目中没有使用)
//#define RT_USING_GDB #endif

RT-thread-2.0.1移植(基于STM32F4xx)的更多相关文章

  1. RT Thread 通过ENV来配置SFUD,操作SPI Flash

    本实验基于正点原子stm32f4探索者板子 请移步我的RT Thread论坛帖子. https://www.rt-thread.org/qa/forum.php?mod=viewthread& ...

  2. 没有二十年功力,写不出Thread.sleep(0)这一行“看似无用”的代码!

    你好呀,我是喜提七天居家隔离的歪歪. 这篇文章要从一个奇怪的注释说起,就是下面这张图: 我们可以不用管具体的代码逻辑,只是单单看这个 for 循环. 在循环里面,专门有个变量 j,来记录当前循环次数. ...

  3. 写个续集,填坑来了!关于“Thread.sleep(0)这一行‘看似无用’的代码”里面留下的坑。

    "我报名参加金石计划1期挑战--瓜分10万奖池,这是我的第2篇文章,点击查看活动详情" 你好呀,我是居家十三天只出了一次小区门的歪歪. 这篇文章是来填坑的,我以前写文章的时候也会去 ...

  4. Thread.Sleep(0) vs Sleep(1) vs Yeild

    本文将要提到的线程及其相关内容,均是指 Windows 操作系统中的线程,不涉及其它操作系统. 文章索引 核心概念 Thread.Yeild       Thread.Sleep(0) Thread. ...

  5. 【转】Thread.sleep(0)的意义

    Thread.sleep(0)的意义 2012-03-23 17:47 2188人阅读 评论(2) 收藏 举报 windows算法unixthread 我们可能经常会用到 Thread.Sleep 函 ...

  6. Thread系列之Thread.Sleep(0)

    线程这一概念,可以理解成进程中的一个小单元.这个单元是一个独立的执行单元,但是与进程中的其他线程共享进程中的内存单元. 由于Cpu资源是有限的,所以进程中的多个线程要抢占Cpu,这也导致进程中的多个线 ...

  7. Thread.sleep(0)的意义& 多线程

    我们可能经常会用到 Thread.Sleep 函数来使线程挂起一段时间.那么你有没有正确的理解这个函数的用法呢?思考下面这两个问题: 假设现在是 2008-4-7 12:00:00.000,如果我调用 ...

  8. 关于Thread.Sleep(0)

    看到的文章,写的不错. 我们可能经常会用到 Thread.Sleep 函数来使线程挂起一段时间.那么你有没有正确的理解这个函数的用法呢?思考下面这两个问题:假设现在是 2008-4-7 12:00:0 ...

  9. 对线程调度中Thread.sleep(0)的深入理解

    在Java或者C#中,都会用到 Thread.Sleep()来使线程挂起一段时间.那么你有没有正确的理解这个方法的用法呢?思考下面这两个问题: 1.假设现在是 2014-8-13 17:00:00.0 ...

  10. Thread系列——Thread.Sleep(0)

    转载自:http://www.cnblogs.com/ATually/archive/2010/10/21/1857261.html 线程这一概念,可以理解成进程中的一个小单元.这个单元是一个独立的执 ...

随机推荐

  1. SpaceVim 发布 v0.8.0

    This project exists thanks to all the people who have contributed. The last release v0.7.0 is target ...

  2. plsql解决中文乱码

    进入 我的电脑,属性,高级,环境变量,添加2项: 1.LANG=zh_CN.GBK 2.NLS_LANG=SIMPLIFIED CHINESE_CHINA.ZHS16GBK

  3. jmeter开发自己的sampler插件

    1. 新建maven工程 2.pom文件引入jmeter的核心包 <project xmlns="http://maven.apache.org/POM/4.0.0" xml ...

  4. java对象创建过程简介

    这是看书的记录,字有点丑啊还是将就搬上来 -.-,等把后面看了完善图

  5. Linux命令应用大词典-第45章 服务器配置

    45.1 ssh-agent:存储用于公钥验证的私钥 45.2 ssh-add:添加RSA或DSA身份的认证代理 45.3 ssh-keyscan:收集主机公钥 45.4 sshd:运行sshd守护进 ...

  6. [CH0304]IncDec Sequence

    和NOIP2018DAY1T1类似的题目,但思维难度高多了. 这题既可以抬高路面,也可以降低路面,而且目标平面不确定,就难起来了. 但是两道题的基本思路几乎一样,同样我们将 2~n 的高度差分,1之所 ...

  7. Linux内核设计笔记12——内存管理

    内存管理学习笔记 页 页是内核管理内存的基本单位,内存管理单元(MMU,管理内存并把虚拟地址转化为物理地址的硬件)通常以页为单位进行处理,从虚拟内存的角度看,页就是最小单位. struct page{ ...

  8. quartz入门实例

    一 Quarta介绍 1 Quartz是什么 Quartz就是一个纯 Java 实现的作业调度工具,相当于数据库中的 Job.Windows 的计划任务.Unix/Linux 下的 Cron,但 Qu ...

  9. [mongodb]child process failed, exited with error number 100

    Run the following command first to start the mongo server mongod run --config /usr/local/etc/mongod. ...

  10. Python中的Comprehensions和Generations

    Python中的Comprehensions和Generations语法都是用来迭代的.Comprehensions语法可用于list,set,dictionary上,而Generations语法分为 ...