菜鸟学STM32之跑马灯

摘要:
是的,也就是说,“点亮一盏LED灯”将通过一个经典的选择程序带您踏上STM32F4的旅程。通过本研究,您将学习如何将STM32F4的IO端口用作输出。我们将使用代码控制STM32F4开发板上的两个LED:DS0和DS1交替闪烁,以实现与字幕类似的效果。此处注意:配置STM32外围设备时,必须随时启用外围设备的时钟!从编译信息中,我们可以看到代码的FLASH大小为5672字节,使用的SRAM大小为1880字节。

微信公众号:小樊Study
关注共同学习,问题或建议,请公众号留言!!!

作为一名程序员,在初步学习编程想必都绕不开一个最为基础的入门级示例“Hello World”,那么,在学习单片机时,最基础的入门示例是什么呢?没错,那就是“点亮一盏LED灯”本次将通过一个经典的跑马灯程序,带大家开启 STM32F4 之旅,通过本次的学习,你将了解到 STM32F4 的 IO 口作为输出使用的方法。
我们将通过代码控制STM32F4 开发板上的两个 LED:DS0 和 DS1 交替闪烁,实现类似跑马灯的效果。

硬件连接

菜鸟学STM32之跑马灯第1张

GPIO工作方式

  • 4种输入模式:
      输入浮空
      输入上拉
      输入下拉
      模拟输入

  • 4种输出模式:
     开漏输出(带上拉或者下拉)
     开漏复用功能(带上拉或者下拉)
     推挽式输出(带上拉或者下拉)
     推挽式复用功能(带上拉或者下拉)

  • 4种最大输出速度:
      -2MHZ
      -25MHz
      -50MHz
      -100MHz

软件设计

led.c

#include "led.h" 
//////////////////////////////////////////////////////////////////////////////////     


//初始化PF9和PF10为输出口.并使能这两个口的时钟            
//LED IO初始化
void LED_Init(void)
{         
  GPIO_InitTypeDef  GPIO_InitStructure;

  RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOF, ENABLE);//使能GPIOF时钟

  //GPIOF9,F10初始化设置
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_9 | GPIO_Pin_10;//LED0和LED1对应IO口
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;//普通输出模式
  GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;//推挽输出
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;//100MHz
  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;//上拉
  GPIO_Init(GPIOF, &GPIO_InitStructure);//初始化GPIO
    
    GPIO_SetBits(GPIOF,GPIO_Pin_9 | GPIO_Pin_10);//GPIOF9,F10设置高,灯灭

}

该代码里面就包含了一个函数 void LED_Init(void),该函数的功能就是用来实现配置 PF9和 PF10 为推挽输出。这里需要注意的是:在配置 STM32 外设的时候,任何时候都要先使能该外设的时钟!GPIO 是挂载在 AHB1 总线上的外设,在固件库中对挂载在 AHB1 总线上的外设时钟使能是通过函数RCC_AHB1PeriphClockCmd ()来实现的。

在设置完时钟之后,LED_Init 调用 GPIO_Init 函数完成对 PF9 和 PF10 的初始化配置,然后调用函数 GPIO_SetBits 控制 LED0 和 LED1 输出 1(LED 灭)。至此,两个 LED 的初始化完毕。这样就完成了对这两个 IO 口的初始化。

led.h

#ifndef __LED_H
#define __LED_H
#include "sys.h"

//////////////////////////////////////////////////////////////////////////////////     
                                  
//////////////////////////////////////////////////////////////////////////////////     


//LED端口定义
#define LED0 PFout(9)    // DS0
#define LED1 PFout(10)    // DS1     

void LED_Init(void);//初始化                             
#endif

这里使用的是位带操作来实现操作某个 IO 口的 1 个位的

在 main 函数里面编写如下代码:

#include "sys.h"
#include "delay.h"
#include "usart.h"
#include "led.h"


//跑马灯实验 -库函数版本

    
int main(void)
{ 
 
    delay_init(168);          //初始化延时函数
    LED_Init();                //初始化LED端口
  while(1)
    {
     LED0=0;              //LED0亮
       LED1=1;                //LED1灭
         delay_ms(500);
         LED0=1;                //LED0灭
         LED1=0;                //LED1亮
         delay_ms(500);
     }
}

代码包含了#include "led.h"这句,使得 LED0、LED1、LED_Init 等能在 main()函数里被调用。这里我们需要重申的是,在固件库中,系统在启动的时候会调用 system_stm32f4xx.c 中的函数SystemInit()对系统时钟进行初始化,在时钟初始化完毕之后会调用 main()函数。所以我们不需要再在 main()函数中调用 SystemInit()函数。当然如果有需要重新设置时钟系统,可以写自己的时钟设置代码,SystemInit()只是将时钟系统初始化为默认状态。main()函数非常简单,先调用 delay_init()初始化延时,接着就是调用 LED_Init()来初始化GPIOF.9 和 GPIOF.10 为输出。最后在死循环里面实现 LED0 和 LED1 交替闪烁,间隔为 500ms。

然后按

菜鸟学STM32之跑马灯第2张

编译工程

菜鸟学STM32之跑马灯第3张

可以看到没有错误,也没有警告。从编译信息可以看出,我们的代码占用 FLASH 大小为:5672 字节(5248+424),所用的 SRAM 大小为:1880 个字节(1832+48)。这里我们解释一下,编译结果里面的几个数据的意义:Code:表示程序所占用 FLASH 的大小(FLASH)。RO-data:即 Read Only-data,表示程序定义的常量(FLASH)。RW-data:即 Read Write-data,表示已被初始化的变量(SRAM)ZI-data:即 Zero Init-data,表示未被初始化的变量(SRAM)有了这个就可以知道你当前使用的 flash 和 sram 大小了,所以,一定要注意的是程序的大小不是.hex 文件的大小,而是编译后的 Code 和 RO-data 之和。

下载验证

菜鸟学STM32之跑马灯第4张

下载完之后,LED0 和 LED1 循环闪烁

菜鸟学STM32之跑马灯第5张

免责声明:文章转载自《菜鸟学STM32之跑马灯》仅用于学习参考。如对内容有疑问,请及时联系本站处理。

上篇java Map及Map.Entry详解JS jQuery查看系统中安装的字体下篇

宿迁高防,2C2G15M,22元/月;香港BGP,2C5G5M,25元/月 雨云优惠码:MjYwNzM=

相关文章

推荐:Java性能优化系列集锦

Java性能问题一直困扰着广大程序员,由于平台复杂性,要定位问题,找出其根源确实很难。随着10多年Java平台的改进以及新出现的多核多处理器,Java软件的性能和扩展性已经今非昔比了。现代JVM持续演进,内建了更为成熟的优化技术、运行时技术和垃圾收集器。与此同时,底层的硬件平台和操作系统也在演化。 目录: 一、Java性能优化系列之一--设计优化 二、J...

TI AM335X 网卡驱动解析

1.CPSW驱动及设备的初始化; (1)首先驱动注册cpsw_driver ,会自动进入cpsw_probe执行; 1 static struct platform_driver cpsw_driver = { 2 .driver = { 3 .name = "cpsw", 4 .owner = T...

[Android6.0][RK3399] 电池系统(三)电量计 CW2015 驱动流程分析【转】

本文转载自:http://blog.csdn.net/dearsq/article/details/72770295 Platform: RK3399OS: Android 6.0Kernel: 4.4Version: v2017.04IC: TI BQ25700、RK808 已知问题 驱动分析函数调用链 已知问题 cw2015 的代码默认是 r...

STM32f103之外部中断

一、背景 有个需求,IO口检测上升沿,然后做相应的动作。在此记录STM32F103的外部中断结构及配置方法, 以备下次快速上手使用。 有许多不太明白,又是老司机(:-D)帮忙,真的是站在别人的肩膀上会让你看的更远,走的更快, 感谢老司机。 二、正文 STM32f103有68个可屏蔽中断。(...

树莓派上传数据错误一例

首先是源码: 1 #-*- utf-8 -*- 2 #env !/usr/bin/python 3 4 importRPi.GPIO as GPIO 5 importtime 6 importjson 7 importdatetime 8 importrequests 9 10 requests.adapters.DEFAULT_RETRIES = 5...

BW:数据源抽取机制 . 沧海

大部分知识源于TBW350和SAP SDN。 对数据源抽取机制的深入探讨 一、什么数据源需要初始化,为什么要进行初始化 有增量机制的数据源就需要初始化,初始化的目的是为了给系统一个时间点,来生成Delta队列。 怎样进行初始化:其实当我们跑I包的时候,Delta队列就建立了,这个和Setup table没有关系 Setup table是怎么回事儿:在LO(...