STM32 基于HAL库和STM32cubeIDE的应用教程 (二)--GPIO的使用

如果有什么不懂的地方欢迎私聊博主,欢迎小白,博主必一一解答。

在 STM32 中,GPIO(通用输入输出)是与外部硬件接口进行交互的主要方式之一。STM32 HAL 库提供了简洁的接口来配置和控制 GPIO 引脚。下面是使用 STM32 HAL 库进行 GPIO 操作的详细教程。

1. 环境准备

确保您已经按照以下步骤准备好开发环境:

  • STM32CubeIDE 已安装。
  • 创建了 STM32 项目,配置了目标 STM32 微控制器或开发板。

2. 配置 GPIO 外设

在 STM32CubeIDE 中,我们通过 STM32CubeMX 来配置 GPIO 引脚。

步骤:
  1. 打开 STM32CubeIDE,选择新建一个 STM32 项目。
  2. Pinout & Configuration 页面,选择您要使用的 GPIO 引脚。例如,选择 GPIOA 上的引脚如 PA5(通常用作 LED 灯),并设置为 GPIO_Output,或 GPIOA 上的引脚如 PA0 设置为 GPIO_Input
  3. Configuration 选项卡中,设置引脚的模式、输出类型等。
    • 对于输出引脚,选择 Push-Pull,并设置速率。
    • 对于输入引脚,选择 Pull-upPull-down,以决定输入信号的默认状态。
  4. Project 设置中,选择项目名称和代码生成选项(选择 STM32CubeIDE 为 IDE,选择 HAL 库作为中间件)。
  5. 点击 Generate Code,STM32CubeMX 会生成初始化代码。

3. HAL 库的 GPIO 操作

生成代码后,您可以开始在 main.c 文件中编写应用程序,利用 STM32 HAL 库操作 GPIO 引脚。

GPIO 输入输出操作

1.初始化 GPIO

STM32CubeMX 会自动生成用于初始化 GPIO 的代码,您只需调用 HAL_GPIO_Init() 函数。例如,在 main.c 中可以看到类似这样的初始化代码,我以注释的方式,解释了代码。

// main.c
#include "main.h"

int main(void)
{
    HAL_Init();  // 初始化 HAL 库
    SystemClock_Config();  // 配置系统时钟
    MX_GPIO_Init();  // 初始化 GPIO

    while (1)
    {
        // 在主循环中进行其他任务
    }
}

void MX_GPIO_Init(void)
{
    GPIO_InitTypeDef GPIO_InitStruct = {0};

    __HAL_RCC_GPIOA_CLK_ENABLE();  // 启用 GPIOA 时钟

    // 配置 PA5 为输出
    GPIO_InitStruct.Pin = GPIO_PIN_5;
    GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;  // 推挽输出
    GPIO_InitStruct.Pull = GPIO_NOPULL;  // 无上下拉
    GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;  // 设置输出速度
    HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);  // 初始化 GPIOA5

    // 配置 PA0 为输入
    GPIO_InitStruct.Pin = GPIO_PIN_0;
    GPIO_InitStruct.Mode = GPIO_MODE_IT_RISING;  // 上升沿中断模式
    GPIO_InitStruct.Pull = GPIO_NOPULL;  // 无上下拉
    HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);  // 初始化 GPIOA0
}

GPIO 输出操作

要设置 GPIO 引脚的输出状态(高电平或低电平),您可以使用 HAL_GPIO_WritePin() 函数。例如:

// 设置 PA5 为高电平(点亮 LED)
HAL_GPIO_WritePin(GPIOA, GPIO_PIN_5, GPIO_PIN_SET);  // 高电平

// 设置 PA5 为低电平(熄灭 LED)
HAL_GPIO_WritePin(GPIOA, GPIO_PIN_5, GPIO_PIN_RESET);  // 低电平

GPIO 输入操作

要读取 GPIO 引脚的输入状态,可以使用 HAL_GPIO_ReadPin() 函数。例如,读取 PA0 的状态:

GPIO_PinState pinState = HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_0);

if (pinState == GPIO_PIN_SET) {
    // 引脚 PA0 为高电平
} else {
    // 引脚 PA0 为低电平
}

GPIO 中断操作

STM32 HAL 库还支持 GPIO 中断。通过 STM32CubeMX 配置中断模式,例如将 PA0 设置为上升沿触发的中断。下面介绍中断的概念。

额外(中断是什么?)

中断(Interrupt)是微控制器(单片机)处理外部事件或任务的一种机制。它允许微控制器在执行程序的过程中,能够中断当前的工作,立即响应外部事件,然后在处理完事件后恢复到原来的工作状态。中断是实时操作系统(RTOS)和高效嵌入式系统设计中常用的一种技术。 

中断的工作原理

当一个中断发生时,微控制器会:

  1. 暂停当前程序:当前正在执行的代码(包括主程序或其他中断服务程序)会被暂停。微控制器保存当前的执行状态(程序计数器、寄存器值等)。

  2. 跳转到中断处理函数(ISR):程序计数器会被修改,跳转到对应的中断服务程序地址。该中断服务程序通常是用户编写的代码,用来处理特定的中断事件。

  3. 处理中断:在中断服务程序中,微控制器执行相应的代码以响应中断,比如读取传感器数据、处理外部设备的请求等。

  4. 恢复执行:中断处理完毕后,微控制器恢复执行原来的程序,继续之前被暂停的操作。

回归正题 ,将 PA0 设置为上升沿触发的中断

在代码中,您需要启用和配置外部中断:

// 在 MX_GPIO_Init 函数中启用中断
HAL_NVIC_SetPriority(EXTI0_1_IRQn, 0, 0);  // 设置中断优先级
HAL_NVIC_EnableIRQ(EXTI0_1_IRQn);  // 启用 EXTI0_1 中断

中断服务程序(ISR)通常放在 stm32f1xx_it.c 中:

// 中断回调函数
void EXTI0_1_IRQHandler(void)
{
    HAL_GPIO_EXTI_IRQHandler(GPIO_PIN_0);  // 处理外部中断
}

// 回调函数,当发生中断时调用
void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
{
    if (GPIO_Pin == GPIO_PIN_0) {
        // 对 PA0 引脚的中断进行处理
    }
}

4. 使用外设和其他功能

  • 配置和使用多个 GPIO 引脚:通过 STM32CubeMX 配置多个 GPIO 引脚进行输入、输出或中断操作。
  • 控制 LED:在 main.c 中使用 HAL_GPIO_WritePin() 控制连接到开发板的 LED。
  • 配置按键:配置外部按键,并在中断或轮询模式下读取按键状态。

5. 示例代码:点亮 LED

下面是一个完整的示例,展示如何通过 GPIO 控制 LED:

#include "main.h"

// 主函数
int main(void)
{
    HAL_Init();  // 初始化 HAL 库
    SystemClock_Config();  // 配置系统时钟
    MX_GPIO_Init();  // 初始化 GPIO

    while (1)
    {
        // 点亮 LED
        HAL_GPIO_WritePin(GPIOA, GPIO_PIN_5, GPIO_PIN_SET);
        HAL_Delay(500);  // 延时 500ms

        // 熄灭 LED
        HAL_GPIO_WritePin(GPIOA, GPIO_PIN_5, GPIO_PIN_RESET);
        HAL_Delay(500);  // 延时 500ms
    }
}

// GPIO 初始化函数
void MX_GPIO_Init(void)
{
    GPIO_InitTypeDef GPIO_InitStruct = {0};

    __HAL_RCC_GPIOA_CLK_ENABLE();  // 启用 GPIOA 时钟

    // 配置 PA5 为输出(LED)
    GPIO_InitStruct.Pin = GPIO_PIN_5;
    GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;  // 推挽输出
    GPIO_InitStruct.Pull = GPIO_NOPULL;  // 无上下拉
    GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;  // 设置输出速度
    HAL_GPIO_Init(GPIOA, &GPIO_InitStruct);  // 初始化 GPIOA5
}

6. 小结

  • GPIO 初始化:通过 STM32CubeMX 配置引脚,并使用 HAL 库函数进行初始化。
  • 输入输出操作:使用 HAL_GPIO_WritePin() 控制输出,使用 HAL_GPIO_ReadPin() 读取输入。
  • 中断处理:通过 STM32CubeMX 配置中断,并在中断回调函数中处理外部中断。

上一篇:生命周期


下一篇:mysql 锁