头像-32385

HelloWii分享铸就美好未来。。。。。。

  • 上海市上海市
  • 单片机 嵌入式 DSP RF/无线
  • 消费电子

个人成就

获得 89 次赞

帮助过40人

CCS 能否更改主题?

CCS 能不能修改主题,像 notepad++ 等等的那还样。。

【新技能get】开发板一起学起来——F429教程第一讲 Blink LED

【新技能get】开发板一起学起来 (第一部分)  本教程作者为ICkey网友@HelloWii ,回帖参与讨论、提问、分享,就能赢取超多丰厚奖励哦~   @HelloWii 也将随时和大家交流学习中的问题。(PS:本教程未经允许谢绝转载) 学教程,送奖励,活动说明详见: 【新技能get√】开发板STM32F429I Discovery技术一起学起来 关键字:IAR第一个项目、数据手册、GPIO、固件库、Blink LED        单片机和开发板等,都是一些工具,既然是工具就要看说明书(数据手册)。如果你的英文很好,那真是太好了,稍加练习读者英文文档也是很无压力。就算英文不是很好,也要尽量的多去看一看英文的原版的东西,因为任何东西都是从不会到会的一个过程。作为四六级都没过的我,看着英文文档开心的也是快要哭了。         关于STM32F429,有时间还是要多参考参考  《Reference Manual  RM0090》 这个官方的数据手册,市面上的书随意翻看基本就会发现,大多都是参考数据手册写的。 由于帖子的内容的过长,就把帖子拆分成了不同的帖子,下面附上链接,点击直达。。。 1. 【新技能get】开发板一起学起来——IAR第一个demo          简介: IAR就不多介绍了关于安装和下载以及如何get 到免(破)费(解)版本的,请度娘吧。我安装的是IAR7.30,里面是可以找到评估板F429的芯片选型,IAR6.30就没了。上面的这篇帖子,就介绍了IAR7.30如何新建一个教程。 下面主要讲的是IAR建立第一个STM32F429的项目程序、以及blink led。由于篇幅有限,关于IAR免(破)费(解)版的安装就不讲详细过程了,这个度娘会告诉你们的。本人安装的是IAR7.30版本的。 IAR全称是IAR Embedded Workbench IDE一个很优秀的集成开发环境(详细的内容可以参考官网:https://www.iar.com/)。 一、Firmware package 简介    准备:已经下载去官网Firmware package(固件库),本人使用的是STM32F429I-Discovery_FW_V1.0.1这个版本的。                 解压开固件库的大致内容如下: 图1-1-1:固件库构成 (注:上图是从手册中copy过来的,可能细节与实际有点出入,但是大体是一样的。) 从上图可以看出,固件库中的资源还是蛮多的。 具体的可以查看下fjjjnk1234的补充哦,,感谢fjjjnk1234(//www.icxbk.com/group-topic-id-49104-page-1#3) 我们知道STM32F429I Discovery预先已经烧录了一个demo程序。我们就用IAR来打开看一下这个demo程序。Demo的路径如下图所示: 图1-1-2:demo程序路径 打开完成之后,编译下载即可在开发板上演示,是不是开心的不行呢。 我们就先学习一下这个例程的配置,再来创建一个我们自己的例程。具体参考参数在工程的右键,查看属性。具体如下所示: 图1-1-3:项目属性 这个属性卡里配置了项目的一些东西,可以详细查看下,这里就不多说了,以下的内容就是参考这个配置做的。 由上面的那么多的学习,这里慢慢新建一个项目。 二、准备文件 首先建立一个文件夹demo,在文件夹里建立 inc、usr、sys三个文件夹如下所示: 图1-1-4:新建文件夹    1.将STM32F429I-Discovery_FW_V1.0.1ProjectsDemonstrationEWARMstm32f4xx_flash.icf 这个文件copy到我们新建的demo目录下。    2.将 STM32F429I-Discovery_FW_V1.0.1LibrariesCMSISInclude 目录下的core_cm4.h 、core_cm4_simd.h、core_cmFunc.h、core_cmInstr.h 复制到 我们建立的目录的demo/inc/文件夹下。    3.将 STM32F429I-Discovery_FW_V1.0.1LibrariesCMSISDeviceSTSTM32F4xxInclude 下的stm32f4xx.h、system_stm32f4xx.h 复制到demo/inc/文件夹下。         inc目录内如如下: 图1-1-5:inc目录内容     4.将 STM32F429I-Discovery_FW_V1.0.1LibrariesCMSISDeviceSTSTM32F4xxSourceTemplates 目录下的system_stm32f4xx.c复制到demo/sys/目录下。     5.将  STM32F429I-Discovery_FW_V1.0.1LibrariesCMSISDeviceSTSTM32F4xxSourceTemplatesiar目录下的startup_stm32f429_439xx.s 复制到 demo/sys/目录下。 三、新建demo 完成了那么多准备工作可以打开IAR新建项目了。      1.打开IAR 7.30新建一个项目 图1-1-6:新建IAR项目     2.将位置保存在我们刚建立的demo文件夹的位置 图1-1-7:保存项目     3.如下图所示,在项目名上右键,添加group 图1-1-8:添加用户组   如下所示: 图1-1-9:添加用户组     4.新建一个main.c的文件,内容如下 #include int main() { while(1); return 0; }    为每个组中,添加相应的文件,鼠标在项目名右键-添加-文件。结果如下: 图1-1-10:添加文件    5.配置工程选项           在项目名称上右键点开属性(options),按如下步骤配置: 图1-1-11:单片机选型 图1-1-12:配置compiler 点选我们前面复制的stm32f4xx_flash.icf这个文件。 图1-1-13:配置Linker 配置Debugger 选择ST-Link 图1-1-14:配置Debugger 勾选Use flash loader(s) 图1-15:配置flash下载 选择SWD模式 图1-1-16:ST-LINK配置 至此点击编译工程如下图所示,没有错误,证明已经建立OK了工程。 图1-1-17:编译工程 2.【新技能get】开发板一起学起来——寄存器点亮LED          简介:点灯,大概是每个单片机开发者,拿到一款新的单片机必用的技能。好,我们也来点个LED,用寄存器来配置一个点灯的程序。 一、硬件连接        STM32F429I Discovery评估板上有两个LED(一个绿色、一个红色),下面的帖子的任务就是点亮这两颗LED,使用的是寄存器来点亮LED。有下面的原理图,可以看到两颗LED与PG13和PG14连接,通过高电平点亮,低电平熄灭。 图1-2-1:LED 电路图 二、时钟       时钟,这个是一个单片机中相当重要的部分。在数字电路中,时钟起到至关重要的作用,正是因为它,才能让这个系统有序的运行。我们来小窥一下STM32F4的时钟树,这是只是简单的介绍,具体还需要自己多去看数据手册研读。直接上图,来看看这棵树: 图1-2-2:时钟树 STM32有5个时钟源:HIS、HSE、MainPLL、LSI、LSE    三个主时钟可以驱动系统 HSI oscillator clock HSE oscillator clock Main PLL (PLL) clock    两个第二时钟源 32 kHz 低速内部RC时钟  (LSI RC) 32.768 kHz 低速外部晶振 (LSE crystal) 三、GPIO(Gneral-Purpose Input Output) 将main函数中的内容更改如下: #include void main () { RCC->AHB1ENR |= 0x00000040; //使能 GPIOG 时钟 GPIOG->MODER &= 0xc3FFFFFF; //配置PG13 PG14 为输出模式 GPIOG->MODER |= 0x14000000; GPIOG->ODR=0xffff4000; // 设置PG14输出高电平 while(1); } 点击编译无措,下载程序到开发板中,就可以看到PG14(RED)被点亮,PG13熄灭 GPIO是算法世界和现实世界的一个桥梁。将你的算法通过IO口和外部交互。IO口 的多少以及功能的多少也是MCU一个重要的因素。 STM32F4xx Family 每一IO口都具有        四个32-bit配置寄存器:GPIOx_MODER、 GPIOx_OTYPER、 GPIOx_OSPEEDR 、GPIOx_PUPDR        两个32-bit 数据寄存器:GPIOx_IDR、GPIOx_ODR        一个 32-bit 复位/置位寄存器:GPIOx_BSRR        一个32-bit 锁存寄存器:GPIOx_LCKR        两个32-bit 功能需选择寄存器:GPIOx_AFRH、GPIOx_AFRL 具体的功能要查看《Reference Manual  RM0090》。 stm32f4xx.h这个就相当于reg52.h里面都是STM32F3的寄存器变量。 RCC->AHB1ENR 学过C的都是都知道  -> 这个是指向的意思,RCC是一个结构体。AHB1ENR是它的一个成员。 具体的我们可以产看stm32f4xx.h文件里面的内容。 在RCC右键,goto 定义的地方,如下图所示: 图1-2-3:goto define  RCC 即可跳转到RCC定义的地方,RCC是RCC_TypeDef 类型的,具体可以查看RCC_TypeDef,会发现AHB1ENR是他的成员变量,如下图所示: 图1-2-4:RCC 图1-2-5:AHB1ENR AHB1ENR寄存器 图1-2-6:AHB1ENR寄存器    MODER寄存器 图1-2-7:MODER寄存器         端口模式控制寄存器                      00:输入(复位模式)                      01:通用输入输出功能                      10:复用模式                      11:模拟模式 ODR寄存器 图1-2-8:ODR寄存器 这个就是数据输出寄存器,,其中[31:16] 为系统保存,[0:15]对应数据的输出。 通过给PG13和PG14 给一个低电平,即可点亮LED。 当然STM32F4功能如此强大,这里只是抛砖引玉的简单的介绍三个寄存器。后面的OTYPER、OSPEEDR、BSRRH、等可以实现上拉下拉输入输出补偿等的一些寄存器,具体可以详细查看数据手册。。。 以上有些内容只是简单的介绍,后面的内容会详细介绍一些上面简单提到的东西。 倘若有什么问题,很高兴你可以跟帖回复,大家一起讨论。。。 后面会详细讲一下时钟树以及SysTick和固件库。由于这几天要出去几天,所以,要等到周六再更新了。 大家有什么问题可以跟帖提问哦。欢迎大家多多来讨论。 3. 【新技能get】开发板一起学起来——固件库点点灯 上一节中,使用了寄存器点灯。简单的介绍了一下寄存器,下面用一个更简单的方法来点灯。 一、固件库添加      首先在以前的文件夹下建立一个stdlib文件夹,将STM32F429I-Discovery_FW_V1.0.1LibrariesSTM32F4xx_StdPeriph_Driver文件夹下的内容复制到 stdlib 文件夹下。在工程文件夹中建立相应的group,然后将刚才添加的文件,添加进来。 如下图所示: 图1-3-1:添加固件库 固件库就是一些API,通过函数可以调用,不像配置寄存器那么麻烦了,但是得掌握和习惯ST公司的函数的书写和命名规则。使用了某个系列的ST公司的单片机的固件库之后,再迁移到ST其它系列的时候,会上手快一些,固件库的命名和功能都是一样或相似的。 如下图可以从文件名就可以相应的功能。 图1-3-1:标准外设固件库 二、时钟简介和配置        SystemInit是system_stm32f4xx.c中的函数。主要的作用是负责系统各种时钟的初始化(系统时钟源选择、PLL倍频和分频、AHB/APB分频器等)。 时钟参数的设置和公式如下: 上面的公式可以表示为: SYSCLK =  (HSE_VALUE or HSI_VALUE / PLL_M) * PLL_N / PLL_P HSE_VALUE = 8000000  由上面的宏定义可以配置得到 系统时钟SYSCLK = 168MHz SystemCoreClockUpdate这个函数根据SystemCoreClock变量的值来更新时钟寄存器。 具体的内容还是参考数据手册的时钟树。 下面为一些默认的设置 HSE_VALUE便是外部时钟的输入值,在stm32f4xx.h定义,可以根据实际修改。 stm32f4xx_rcc.c  这个文件中包含了时钟的配置。 RCC(Reset and clock control) void RCC_RTCCLKConfig(uint32_t RCC_RTCCLKSource); void RCC_RTCCLKCmd(FunctionalState NewState); void RCC_BackupResetCmd(FunctionalState NewState); void RCC_I2SCLKConfig(uint32_t RCC_I2SCLKSource); void RCC_SAIPLLI2SClkDivConfig(uint32_t RCC_PLLI2SDivQ); void RCC_SAIPLLSAIClkDivConfig(uint32_t RCC_PLLSAIDivQ); void RCC_SAIBlockACLKConfig(uint32_t RCC_SAIBlockACLKSource); void RCC_SAIBlockBCLKConfig(uint32_t RCC_SAIBlockBCLKSource); void RCC_LTDCCLKDivConfig(uint32_t RCC_PLLSAIDivR); void RCC_TIMCLKPresConfig(uint32_t RCC_TIMCLKPrescaler); void RCC_AHB1PeriphClockCmd(uint32_t RCC_AHB1Periph, FunctionalState NewState); void RCC_AHB2PeriphClockCmd(uint32_t RCC_AHB2Periph, FunctionalState NewState); void RCC_AHB3PeriphClockCmd(uint32_t RCC_AHB3Periph, FunctionalState NewState); void RCC_APB1PeriphClockCmd(uint32_t RCC_APB1Periph, FunctionalState NewState); void RCC_APB2PeriphClockCmd(uint32_t RCC_APB2Periph, FunctionalState NewState); void RCC_AHB1PeriphResetCmd(uint32_t RCC_AHB1Periph, FunctionalState NewState); void RCC_AHB2PeriphResetCmd(uint32_t RCC_AHB2Periph, FunctionalState NewState); void RCC_AHB3PeriphResetCmd(uint32_t RCC_AHB3Periph, FunctionalState NewState); void RCC_APB1PeriphResetCmd(uint32_t RCC_APB1Periph, FunctionalState NewState); void RCC_APB2PeriphResetCmd(uint32_t RCC_APB2Periph, FunctionalState NewState); void RCC_AHB1PeriphClockLPModeCmd(uint32_t RCC_AHB1Periph, FunctionalState NewState); void RCC_AHB2PeriphClockLPModeCmd(uint32_t RCC_AHB2Periph, FunctionalState NewState); void RCC_AHB3PeriphClockLPModeCmd(uint32_t RCC_AHB3Periph, FunctionalState NewState); void RCC_APB1PeriphClockLPModeCmd(uint32_t RCC_APB1Periph, FunctionalState NewState); void RCC_APB2PeriphClockLPModeCmd(uint32_t RCC_APB2Periph, FunctionalState NewState); RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOG,ENABLE);  来使能外设GPIOG的时钟。详细的请查看User manual的时钟树。 #include int main() { GPIO_InitTypeDef GPIO_Structure; GPIO_Structure.GPIO_Pin = GPIO_Pin_13|GPIO_Pin_14; GPIO_Structure.GPIO_Mode = GPIO_Mode_OUT; SystemInit(); RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOG,ENABLE); // enable GPIOG clock GPIO_Init(GPIOG,&GPIO_Structure); GPIO_ResetBits(GPIOG,GPIO_Pin_13); // 输出低电平 GPIO_SetBits(GPIOG,GPIO_Pin_14); //输出高电平 点亮红色LED while(1); } 对应相应的固件库,API的调用虽然ST没有给一本关于API的的说明性PDF。 但是每个 对应 .c 文件都是介绍的相当详细,比如stm32f4xx_gpio.c,中就介绍了IO口的使用方法(不过是英文的),如下: 学习MCU,尽量多去参考官方的资料,别人讲的东西,其实也是参考官方的资料的。 至此便用了固件库来点亮了LED,相比较寄存器来说还是简单了一些。使用固件库呢还是寄存器呢,这个就看个人的习惯和爱好了。 4. 【新技能get】开发板一起学起来——BLINK LED 讲了那么多了,好吧,现在我们来一起闪烁一下LED吧。 给一个灯不停的通高低电平即可以实现LED的闪烁。 最简单的一种方法就是使用延时,让CPU在哪里不停的做一些无用功,可以实现延时,让LED闪烁,程序如下所示: #include void delay_ms(unsigned int m) { unsigned int i,j; while(m--) { i=168; while(i--) { j=100; while(j--); } } } int main() { GPIO_InitTypeDef GPIO_Structure; GPIO_Structure.GPIO_Pin = GPIO_Pin_13|GPIO_Pin_14; GPIO_Structure.GPIO_Mode = GPIO_Mode_OUT; SystemInit(); RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOG,ENABLE); // enable GPIOG clock GPIO_Init(GPIOG,&GPIO_Structure); while(1) { delay_ms(500); GPIO_ResetBits(GPIOG,GPIO_Pin_13); //low delay_ms(500); GPIO_SetBits(GPIOG,GPIO_Pin_13); // high } return 0; } 以上代码便可以实现简单的LED闪烁。 当然这种方法并不是很好,因为CPU在不停的做减法,做一些无用的功,白白的牺牲了CPU 资源。 下面就介绍一个SyStick。 SysTick是一个24-bit 的系统自减定时器,它是集成在Cortex-M 内核的内部的,并不是片内外设。可以用来产生一些定时中断,一般用作操作系统的时钟节拍。 图1-4-1:SyStick寄存器 图1-4-2:Systick 寄存器描述 CTRL:   控制寄存器,         默认0x0000004 LOAD:  重载寄存器,         默认0x0000000 VAL:    当前值寄存器,      默认0x0000000 CALIB: 校准值寄存器,      默认0x0002328 图1-4-3:向量优先级 #include unsigned int Ts_Gb; void delay_ms(uint32_t m) { Ts_Gb = m; while(Ts_Gb != 0); } void SysTick_Handler(void) { if (Ts_Gb != 0x00) { Ts_Gb--; } } int main() { GPIO_InitTypeDef GPIO_Structure; GPIO_Structure.GPIO_Pin = GPIO_Pin_13|GPIO_Pin_14; GPIO_Structure.GPIO_Mode = GPIO_Mode_OUT; SystemInit(); SysTick_Config(SystemCoreClock/1000); RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOG,ENABLE); // enable GPIOG clock RCC_AHB2PeriphClockCmd(RCC_APB2Periph_SYSCFG,ENABLE); //enable SYSCFG CLock GPIO_Init(GPIOG,&GPIO_Structure); while(1) { delay_ms(500); GPIO_ResetBits(GPIOG,GPIO_Pin_13); //low delay_ms(500); GPIO_SetBits(GPIOG,GPIO_Pin_13); // high } return 0; } 以上便可以实现通过中断来实现延时。          SysTick_Config(SystemCoreClock/1000);      RCC_AHB2PeriphClockCmd(RCC_APB2Periph_SYSCFG,ENABLE); //enable SYSCFG CLock      设置为时钟的千分之一。使能时钟。     SysTick_Handler()每一秒被执行一千次,从而通过delay_ms()来实现间接的延时。 下载到开发板中,既可以看到开发板LED闪烁。 其他内容: 【新技能get】开发板一起学起来——STM32F429 Discovery简介