STM32-06-STM32_GPIO

文章目录

  • STM32 GPIO
    • 1. GPIO简介
    • 2. GPIO工作模式
    • 3. GPIO相关寄存器
    • 4. 通用外设驱动模型
    • 5. GPIO配置步骤
    • 6. 点亮LED灯
    • 7. LED流水灯
    • 8. 按键控制LED灯

STM32 GPIO

1. GPIO简介

  • 什么是GPIO?

    GPIO:General Purpose Input Output,即通用输入输出端口,简称GPIO

    作用:负责采集外部器件的信息或者控制外部器件工作,即输入输出

    STM32-06-STM32_GPIO_第1张图片

    STM32F103ZET6芯片是144脚的芯片,具有GPIOA、GPIOB、GPIOC、GPIOD、GPIOE、GPIOF和GPIOG七组GPIO口,共有112个IO口可供编程使用。

  • GPIO特点?

    1. 不同型号芯片IO口数量可能不一样
    2. 快速翻转
    3. 每个IO口都可以做中断
    4. 支持8种工作模式
  • GPIO电气特性?

    1. STM32工作电压范围:2 V <= VDD <= 3.6 V

    2. GPIO识别电压范围:CMOS端口:-0.3 V <= 低电平 <= 1.164 V 1.833 V <= 高电平 <= 3.6 V

    3. GPIO输出电流:单个IO,最大25mA

  • GPIO引脚分布?

    STM32引脚类型:电源引脚、晶振引脚、复位引脚、下载引脚、BOOT引脚、GPIO引脚

2. GPIO工作模式

  1. 浮空输入
    STM32-06-STM32_GPIO_第2张图片

  2. 上拉输入
    STM32-06-STM32_GPIO_第3张图片

  3. 下拉输入
    STM32-06-STM32_GPIO_第4张图片

  4. 模拟输入
    STM32-06-STM32_GPIO_第5张图片

  5. 开漏输出
    STM32-06-STM32_GPIO_第6张图片

  6. 复用开漏输出
    STM32-06-STM32_GPIO_第7张图片

  7. 推挽输出
    STM32-06-STM32_GPIO_第8张图片

  8. 复用推挽输出
    STM32-06-STM32_GPIO_第9张图片

3. GPIO相关寄存器

CRL CRH IDR ODR BSRR BRR LCKR
配置工作模式,输出速度 配置工作模式,输出速度 输入数据 输出数据 设置ODR寄存器的值 F4之后没有这个寄存器,考虑代码兼容性的话不建议使用 配置锁定,用得不多
  • CRL寄存器

作用:配置GPIOxPx0~Px7工作模式输出速度
STM32-06-STM32_GPIO_第10张图片

  • CRH寄存器

    作用:配置GPIOxPx8~Px15工作模式输出速度
    STM32-06-STM32_GPIO_第11张图片

  • IDR寄存器
    STM32-06-STM32_GPIO_第12张图片

  • ODR寄存器

    STM32-06-STM32_GPIO_第13张图片

  • BSRR寄存器
    STM32-06-STM32_GPIO_第14张图片

4. 通用外设驱动模型

  1. 初始化:时钟设置、参数设置、IO设置(可选)、中断设置(可选)
  2. 读函数(可选):从外设读取数据
  3. 写函数(可选):往外设写入数据
  4. 中断服务函数(可选):根据中断标志,处理外设各种中断事物

5. GPIO配置步骤

  • 配置步骤

    1. 使能时钟 __HAL_RCC_GPIOx_CLK_ENABLE()
    2. 设置工作模式 HAL_GPIO_Init()
    3. 设置输出状态(可选) HAL_GPIO_WritePin() HAL_GPIO_TogglePin()
    4. 读取输入状态 HAL_GPIO_ReadPin()
  • 相关HAL库函数

    HAL库驱动函数 主要寄存器 功能
    __HAL_RCC_GPIOx_CLK_ENABLE() F1:RCC_APB2ENR F4:RCC_AHB1ENR F7:RCC_AHB1ENR H7:RCC_AHB4ENR 开启GPIO时钟
    HAL_GPIO_Init(…) F1:CRL、CRH、ODR F4/F7/H7:MODER、OTYPER、OSPEEDR、PUPDR 初始化GPIO
    HAL_GPIO_WritePin(…) BSRR 控制IO输出高/低电平
    HAL_GPIO_TogglePin(…) BSRR 每次调用IO输出电平翻转一次
    HAL_GPIO_ReadPin(…) IDR 读取IO电平
  • 具体配置步骤,以GPIOA为例

    1. 使能时钟:__HAL_RCC_GPIOx_CLK_ENABLE()

      #define __HAL_RCC_GPIOA_CLK_ENABLE()   
      do { \
               __IO uint32_t tmpreg; \
               SET_BIT(RCC->APB2ENR, RCC_APB2ENR_IOPAEN);\
                /* Delay after an RCC peripheral clock enabling */\
                tmpreg = READ_BIT(RCC->APB2ENR, RCC_APB2ENR_IOPAEN);\
                UNUSED(tmpreg); \
               } while(0U)
      

      主要代码为SET_BIT(RCC->APB2ENR, RCC_APB2ENR_IOPAEN);,此代码第一个参数为APB2外设使能寄存器,第二个参数代表偏移量,使能这个寄存器的哪一位由这个偏移量来决定。使能GPIOA的时钟时,偏移量为2.

      #define RCC_APB2ENR_IOPAEN_Pos  (2U)                              
      #define RCC_APB2ENR_IOPAEN_Msk  (0x1UL << RCC_APB2ENR_IOPAEN_Pos)/*!< 0x00000004 */
      #define RCC_APB2ENR_IOPAEN      RCC_APB2ENR_IOPAEN_Msk /*!< I/O port A clock enable */
      
    2. 设置工作模式:HAL_GPIO_Init()

      void HAL_GPIO_Init(GPIO_TypeDef  *GPIOx, GPIO_InitTypeDef *GPIO_Init)
      {
        uint32_t position = 0x00u;
        uint32_t ioposition;
        uint32_t iocurrent;
        uint32_t temp;
        uint32_t config = 0x00u;
        __IO uint32_t *configregister; /* Store the address of CRL or CRH register based on pin number */
        uint32_t registeroffset;       /* offset used during computation of CNF and MODE bits placement inside CRL or CRH register */
      
        /* Check the parameters */
        assert_param(IS_GPIO_ALL_INSTANCE(GPIOx));
        assert_param(IS_GPIO_PIN(GPIO_Init->Pin));
        assert_param(IS_GPIO_MODE(GPIO_Init->Mode));
      
        /* Configure the port pins */
        while (((GPIO_Init->Pin) >> position) != 0x00u)
        {
          /* Get the IO position */
          ioposition = (0x01uL << position);
      
          /* Get the current IO position */
          iocurrent = (uint32_t)(GPIO_Init->Pin) & ioposition;
      
          if (iocurrent == ioposition)
          {
            /* Check the Alternate function parameters */
            assert_param(IS_GPIO_AF_INSTANCE(GPIOx));
      
            /* Based on the required mode, filling config variable with MODEy[1:0] and CNFy[3:2] corresponding bits */
            switch (GPIO_Init->Mode)
            {
              /* If we are configuring the pin in OUTPUT push-pull mode */
              case GPIO_MODE_OUTPUT_PP:
                /* Check the GPIO speed parameter */
                assert_param(IS_GPIO_SPEED(GPIO_Init->Speed));
                config = GPIO_Init->Speed + GPIO_CR_CNF_GP_OUTPUT_PP;
                break;
      
              /* If we are configuring the pin in OUTPUT open-drain mode */
              case GPIO_MODE_OUTPUT_OD:
                /* Check the GPIO speed parameter */
                assert_param(IS_GPIO_SPEED(GPIO_Init->Speed));
                config = GPIO_Init->Speed + GPIO_CR_CNF_GP_OUTPUT_OD;
                break;
      
              /* If we are configuring the pin in ALTERNATE FUNCTION push-pull mode */
              case GPIO_MODE_AF_PP:
                /* Check the GPIO speed parameter */
                assert_param(IS_GPIO_SPEED(GPIO_Init->Speed));
                config = GPIO_Init->Speed + GPIO_CR_CNF_AF_OUTPUT_PP;
                break;
      
              /* If we are configuring the pin in ALTERNATE FUNCTION open-drain mode */
              case GPIO_MODE_AF_OD:
                /* Check the GPIO speed parameter */
                assert_param(IS_GPIO_SPEED(GPIO_Init->Speed));
                config = GPIO_Init->Speed + GPIO_CR_CNF_AF_OUTPUT_OD;
                break;
      
              /* If we are configuring the pin in INPUT (also applicable to EVENT and IT mode) */
              case GPIO_MODE_INPUT:
              case GPIO_MODE_IT_RISING:
              case GPIO_MODE_IT_FALLING:
              case GPIO_MODE_IT_RISING_FALLING:
              case GPIO_MODE_EVT_RISING:
              case GPIO_MODE_EVT_FALLING:
              case GPIO_MODE_EVT_RISING_FALLING:
                /* Check the GPIO pull parameter */
                assert_param(IS_GPIO_PULL(GPIO_Init->Pull));
                if (GPIO_Init->Pull == GPIO_NOPULL)
                {
                  config = GPIO_CR_MODE_INPUT + GPIO_CR_CNF_INPUT_FLOATING;
                }
                else if (GPIO_Init->Pull == GPIO_PULLUP)
                {
                  config = GPIO_CR_MODE_INPUT + GPIO_CR_CNF_INPUT_PU_PD;
      
                  /* Set the corresponding ODR bit */
                  GPIOx->BSRR = ioposition;
                }
                else /* GPIO_PULLDOWN */
                {
                  config = GPIO_CR_MODE_INPUT + GPIO_CR_CNF_INPUT_PU_PD;
      
                  /* Reset the corresponding ODR bit */
                  GPIOx->BRR = ioposition;
                }
                break;
      
              /* If we are configuring the pin in INPUT analog mode */
              case GPIO_MODE_ANALOG:
                config = GPIO_CR_MODE_INPUT + GPIO_CR_CNF_ANALOG;
                break;
      
              /* Parameters are checked with assert_param */
              default:
                break;
            }
      
            /* Check if the current bit belongs to first half or last half of the pin count number
             in order to address CRH or CRL register*/
            configregister = (iocurrent < GPIO_PIN_8) ? &GPIOx->CRL     : &GPIOx->CRH;
            registeroffset = (iocurrent < GPIO_PIN_8) ? (position << 2u) : ((position - 8u) << 2u);
      
            /* Apply the new configuration of the pin to the register */
            MODIFY_REG((*configregister), ((GPIO_CRL_MODE0 | GPIO_CRL_CNF0) << registeroffset), (config << registeroffset));
      
            /*--------------------- EXTI Mode Configuration ------------------------*/
            /* Configure the External Interrupt or event for the current IO */
            if ((GPIO_Init->Mode & EXTI_MODE) == EXTI_MODE)
            {
              /* Enable AFIO Clock */
              __HAL_RCC_AFIO_CLK_ENABLE();
              temp = AFIO->EXTICR[position >> 2u];
              CLEAR_BIT(temp, (0x0Fu) << (4u * (position & 0x03u)));
              SET_BIT(temp, (GPIO_GET_INDEX(GPIOx)) << (4u * (position & 0x03u)));
              AFIO->EXTICR[position >> 2u] = temp;
      
      
              /* Configure the interrupt mask */
              if ((GPIO_Init->Mode & GPIO_MODE_IT) == GPIO_MODE_IT)
              {
                SET_BIT(EXTI->IMR, iocurrent);
              }
              else
              {
                CLEAR_BIT(EXTI->IMR, iocurrent);
              }
      
              /* Configure the event mask */
              if ((GPIO_Init->Mode & GPIO_MODE_EVT) == GPIO_MODE_EVT)
              {
                SET_BIT(EXTI->EMR, iocurrent);
              }
              else
              {
                CLEAR_BIT(EXTI->EMR, iocurrent);
              }
      
              /* Enable or disable the rising trigger */
              if ((GPIO_Init->Mode & RISING_EDGE) == RISING_EDGE)
              {
                SET_BIT(EXTI->RTSR, iocurrent);
              }
              else
              {
                CLEAR_BIT(EXTI->RTSR, iocurrent);
              }
      
              /* Enable or disable the falling trigger */
              if ((GPIO_Init->Mode & FALLING_EDGE) == FALLING_EDGE)
              {
                SET_BIT(EXTI->FTSR, iocurrent);
              }
              else
              {
                CLEAR_BIT(EXTI->FTSR, iocurrent);
              }
            }
          }
      
      	position++;
        }
      }
      

      此函数有两个参数,都为结构体指针类型,第一个参数代表GPIO所使用的寄存器的基地址,第二个参数代表GPIO模式配置,GPIO相关寄存器上述已经详细描述各个寄存器代表的功能和用途,下面列出相关结构体定义。

      typedef struct
      {
        __IO uint32_t CRL;  //HAL_GPIO_Init()函数使用
        __IO uint32_t CRH;  //HAL_GPIO_Init()函数使用
        __IO uint32_t IDR;  //HAL_GPIO_ReadPin()函数使用
        __IO uint32_t ODR;  //HAL_GPIO_Init()函数使用
        __IO uint32_t BSRR; //HAL_GPIO_WritePin()和HAL_GPIO_TogglePin()函数使用
        __IO uint32_t BRR;  //一般情况下不使用
        __IO uint32_t LCKR; //一般情况下不使用
      } GPIO_TypeDef;
      

      下面介绍GPIO初始化配置结构体,里面包含四个成员变量,第一个成员变量为引脚号,第二个成员变量为模式设置,第三个成员变量为上拉下拉设置,第四个成员变量为速度设置,每一个成员变量的值都是固定的,不是任意设置的,都有相关的宏定义,下面一一介绍相关宏定义。

      typedef struct
      {
        uint32_t Pin;      //引脚号 
        uint32_t Mode;     //模式设置   
        uint32_t Pull;     //上拉下拉设置 
        uint32_t Speed;    //速度设置 
      } GPIO_InitTypeDef;
      

      引脚号取值范围:

      #define GPIO_PIN_0             ((uint16_t)0x0001)  /* Pin 0 selected    */
      #define GPIO_PIN_1             ((uint16_t)0x0002)  /* Pin 1 selected    */
      #define GPIO_PIN_2             ((uint16_t)0x0004)  /* Pin 2 selected    */
      #define GPIO_PIN_3             ((uint16_t)0x0008)  /* Pin 3 selected    */
      #define GPIO_PIN_4             ((uint16_t)0x0010)  /* Pin 4 selected    */
      #define GPIO_PIN_5             ((uint16_t)0x0020)  /* Pin 5 selected    */
      #define GPIO_PIN_6             ((uint16_t)0x0040)  /* Pin 6 selected    */
      #define GPIO_PIN_7             ((uint16_t)0x0080)  /* Pin 7 selected    */
      #define GPIO_PIN_8             ((uint16_t)0x0100)  /* Pin 8 selected    */
      #define GPIO_PIN_9             ((uint16_t)0x0200)  /* Pin 9 selected    */
      #define GPIO_PIN_10            ((uint16_t)0x0400)  /* Pin 10 selected   */
      #define GPIO_PIN_11            ((uint16_t)0x0800)  /* Pin 11 selected   */
      #define GPIO_PIN_12            ((uint16_t)0x1000)  /* Pin 12 selected   */
      #define GPIO_PIN_13            ((uint16_t)0x2000)  /* Pin 13 selected   */
      #define GPIO_PIN_14            ((uint16_t)0x4000)  /* Pin 14 selected   */
      #define GPIO_PIN_15            ((uint16_t)0x8000)  /* Pin 15 selected   */
      #define GPIO_PIN_All           ((uint16_t)0xFFFF)  /* All pins selected */
      

      模式设置取值范围:

      #define  GPIO_MODE_INPUT               0x00000000u      //配合pull设置上拉下拉浮空输入
      #define  GPIO_MODE_OUTPUT_PP           0x00000001u      //推挽输出
      #define  GPIO_MODE_OUTPUT_OD           0x00000011u      //开漏输出
      #define  GPIO_MODE_AF_PP               0x00000002u      //复用推挽输出
      #define  GPIO_MODE_AF_OD               0x00000012u      //复用开漏输出
      #define  GPIO_MODE_AF_INPUT            GPIO_MODE_INPUT         
      
      #define  GPIO_MODE_ANALOG              0x00000003u      //模拟输入
      
      //以下为外部中断或外部事件模式
      #define  GPIO_MODE_IT_RISING           0x10110000u   
      #define  GPIO_MODE_IT_FALLING          0x10210000u   
      #define  GPIO_MODE_IT_RISING_FALLING   0x10310000u  
      
      #define  GPIO_MODE_EVT_RISING          0x10120000u   
      #define  GPIO_MODE_EVT_FALLING         0x10220000u   
      #define  GPIO_MODE_EVT_RISING_FALLING  0x10320000u   
      

      上拉下拉设置取值范围:

      #define  GPIO_NOPULL   0x00000000u   //浮空输入
      #define  GPIO_PULLUP   0x00000001u   //上拉输入
      #define  GPIO_PULLDOWN 0x00000002u   //下拉输入
      

      速度设置取值范围:

      #define  GPIO_SPEED_FREQ_LOW      (GPIO_CRL_MODE0_1) //低速
      #define  GPIO_SPEED_FREQ_MEDIUM   (GPIO_CRL_MODE0_0) //中速
      #define  GPIO_SPEED_FREQ_HIGH     (GPIO_CRL_MODE0)   //高速
      
    3. 设置输出状态: HAL_GPIO_WritePin() HAL_GPIO_TogglePin()

      HAL_GPIO_WritePin()函数有三个参数,第一个参数为上述所提的寄存器基地址,第二个参数为引脚号,第三个参数为要写入的值(GPIO状态:0或1).

      void HAL_GPIO_WritePin(GPIO_TypeDef *GPIOx, uint16_t GPIO_Pin, GPIO_PinState PinState)
      {
        /* Check the parameters */
        assert_param(IS_GPIO_PIN(GPIO_Pin));
        assert_param(IS_GPIO_PIN_ACTION(PinState));
      
        if (PinState != GPIO_PIN_RESET)
        {
          GPIOx->BSRR = GPIO_Pin;
        }
        else
        {
          GPIOx->BSRR = (uint32_t)GPIO_Pin << 16u;
        }
      }
      

      HAL_GPIO_TogglePin()函数有两个参数,第一个参数为上述所提的寄存器基地址,第二个参数为引脚号.

      void HAL_GPIO_TogglePin(GPIO_TypeDef *GPIOx, uint16_t GPIO_Pin)
      {
        uint32_t odr;
      
        /* Check the parameters */
        assert_param(IS_GPIO_PIN(GPIO_Pin));
      
        /* get current Ouput Data Register value */
        odr = GPIOx->ODR;
      
        /* Set selected pins that were at low level, and reset ones that were high */
        GPIOx->BSRR = ((odr & GPIO_Pin) << GPIO_NUMBER) | (~odr & GPIO_Pin);
      }
      
    4. 读取输入状态: HAL_GPIO_ReadPin()

      HAL_GPIO_ReadPin()函数有两个参数,第一个参数为上述所提的寄存器基地址,第二个参数为引脚号.

      GPIO_PinState HAL_GPIO_ReadPin(GPIO_TypeDef *GPIOx, uint16_t GPIO_Pin)
      {
        GPIO_PinState bitstatus;
      
        /* Check the parameters */
        assert_param(IS_GPIO_PIN(GPIO_Pin));
      
        if ((GPIOx->IDR & GPIO_Pin) != (uint32_t)GPIO_PIN_RESET)
        {
          bitstatus = GPIO_PIN_SET;
        }
        else
        {
          bitstatus = GPIO_PIN_RESET;
        }
        return bitstatus;
      }
      

6. 点亮LED灯

  • 硬件连接图

    从硬件电路图可以看出,STM32F1开发板包含三个LED灯,一个蓝色的电源指示灯,一个红色,一个绿色。电源指示灯接地,上电后就会点亮。红灯和绿灯一端共阳,一端由PB5PE5控制,只要给PB5和PE5接低电平,LED0和LED1就会亮。
    STM32-06-STM32_GPIO_第15张图片

  • 代码配置步骤

    1. 使能时钟

      //使能时钟
      __HAL_RCC_GPIOB_CLK_ENABLE();
      
    2. 设置工作模式

      //配置工作模式
      GPIO_InitTypeDef gpio_init_struct;
      gpio_init_struct.Pin = GPIO_PIN_5;
      gpio_init_struct.Mode = GPIO_MODE_OUTPUT_PP;
      gpio_init_struct.Speed = GPIO_SPEED_FREQ_LOW;
      HAL_GPIO_Init(GPIOB, &gpio_init_struct);
      
      //设置初始化状态
      HAL_GPIO_WritePin(GPIOB, GPIO_PIN_5, GPIO_PIN_SET);
      
    3. 设置输出状态

      //点亮LED0
      HAL_GPIO_WritePin(GPIOB,GPIO_PIN_5,GPIO_PIN_RESET);
      
  • 实验结果展示

7. LED流水灯

  • 代码配置步骤

    1. 使能时钟

      //使能时钟
      __HAL_RCC_GPIOB_CLK_ENABLE();
      __HAL_RCC_GPIOE_CLK_ENABLE();
      
    2. 设置工作模式

      //配置工作模式
      //引脚设置为第五个引脚
      gpio_init_struct.Pin = GPIO_PIN_5;
      //推挽输出
      gpio_init_struct.Mode = GPIO_MODE_OUTPUT_PP;
      //低速模式
      gpio_init_struct.Speed = GPIO_SPEED_FREQ_LOW;
      //往结构体传值
      HAL_GPIO_Init(GPIOB, &gpio_init_struct);
      
      gpio_init_struct.Pin = GPIO_PIN_5;
      gpio_init_struct.Mode = GPIO_MODE_OUTPUT_PP;
      gpio_init_struct.Speed = GPIO_SPEED_FREQ_LOW;
      HAL_GPIO_Init(GPIOE, &gpio_init_struct);
      
      //设置初始化状态
      HAL_GPIO_WritePin(GPIOB, GPIO_PIN_5, GPIO_PIN_SET);
      HAL_GPIO_WritePin(GPIOE, GPIO_PIN_5, GPIO_PIN_SET);	
      
    3. 设置输出状态

      //直接使用HAL_GPIO_TogglePin()函数进行翻转
      HAL_GPIO_TogglePin(GPIOB, GPIO_PIN_5);
      delay_ms(300);
      HAL_GPIO_TogglePin(GPIOE, GPIO_PIN_5);
      delay_ms(300);
      
  • 实验结果展示

8. 按键控制LED灯

  • 硬件连接图

    KEY_UP按键一端接的高电平,当检测到PA0为1时,代表按键按下。KEY0KEY1KEY2按键共地,当检测到PE4、PE3、PE2为0时,代表按键按下。
    STM32-06-STM32_GPIO_第16张图片

    执行按键操作时,需要使用软件消抖,就是通过延时跳过抖动的时间段,再判断IO输入电平。
    STM32-06-STM32_GPIO_第17张图片

  • 代码配置

    按键初始化函数

    void key_init(void)
    {
        GPIO_InitTypeDef gpio_init_struct;
        
        //使能时钟
        __HAL_RCC_GPIOE_CLK_ENABLE();
        __HAL_RCC_GPIOA_CLK_ENABLE();
        
        //配置工作模式
        gpio_init_struct.Pin = GPIO_PIN_3;
        gpio_init_struct.Mode = GPIO_MODE_INPUT;
        //配置上拉输入
        gpio_init_struct.Pull = GPIO_PULLUP;
        HAL_GPIO_Init(GPIOE, &gpio_init_struct);
        
        //配置工作模式
        gpio_init_struct.Pin = GPIO_PIN_0;
        gpio_init_struct.Mode = GPIO_MODE_INPUT;
        //配置下拉输入
        gpio_init_struct.Pull = GPIO_PULLDOWN;
        HAL_GPIO_Init(GPIOA, &gpio_init_struct);
    }
    

    红色LED按键控制函数

    uint8_t key_scan_red_led(void)
    {
        if(HAL_GPIO_ReadPin(GPIOE, GPIO_PIN_3) == 0)
        {
            delay_ms(10);  //消抖
            if(HAL_GPIO_ReadPin(GPIOE, GPIO_PIN_3) == 0)
            {
                while(HAL_GPIO_ReadPin(GPIOE, GPIO_PIN_3) == 0);  //等待按键松开
                return 1;   //按键按下返回
            }
        }
    
        return 0;
    }
    

    绿色LED按键控制函数

    uint8_t key_scan_green_led(void)
    {
        if(HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_0) == 1)
        {
            delay_ms(10);  //消抖
            if(HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_0) == 1)
            {
                while(HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_0) == 1);
                return 1;   //按键按下返回
            }
        }
        
        return 0;
    }
    

    主函数

    int main(void)
    {
        HAL_Init();                         /* 初始化HAL库 */
        sys_stm32_clock_init(RCC_PLL_MUL9); /* 设置时钟, 72Mhz */
        delay_init(72);                     /* 延时初始化 */
        led_init();                         /* LED初始化 */
        key_init();
        
        while(1)
        {
            //判断控制红色LED的按键是否按下
            if (key_scan_red_led())
            {
                HAL_GPIO_WritePin(GPIOB,GPIO_PIN_5,GPIO_PIN_RESET);   
                delay_ms(100);
                HAL_GPIO_WritePin(GPIOB,GPIO_PIN_5,GPIO_PIN_SET);
            }
            //判断控制绿色LED的按键是否按下
            if(key_scan_green_led())
            {
                HAL_GPIO_WritePin(GPIOE,GPIO_PIN_5,GPIO_PIN_RESET);    
                delay_ms(100);
                HAL_GPIO_WritePin(GPIOE,GPIO_PIN_5,GPIO_PIN_SET);
            }
        }
    }
    
  • 实验结果展示

声明:资料来源(战舰STM32F103ZET6开发板资源包)

  1. Cortex-M3权威指南(中文).pdf
  2. STM32F10xxx参考手册_V10(中文版).pdf
  3. STM32F103 战舰开发指南V1.3.pdf
  4. STM32F103ZET6(中文版).pdf
  5. 战舰V4 硬件参考手册_V1.0.pdf

你可能感兴趣的:(嵌入式,stm32,嵌入式硬件,单片机)