一、GPIO简介
GPIO 是通用输入输出端口的简称,简单来说就是 STM32 可控制的引脚,STM32 芯片的 GPIO 引 脚与外部设备连接起来,从而实现与外部通讯、控制以及数据采集的功能。STM32 芯片的 GPIO 被分成很多组,每组有 16 个引脚,如型号为 STM32F4IGT6 型号的芯片有 GPIOA、GPIOB、GPIOC 至 GPIOI 共 9 组 GPIO,芯片一共 176 个引脚,其中 GPIO 就占了一大部分,所有的 GPIO 引脚都 有基本的输入输出功能。
最基本的输出功能是由 STM32 控制引脚输出高、低电平,实现开关控制,如把 GPIO 引脚接入 到 LED 灯,那就可以控制 LED 灯的亮灭,引脚接入到继电器或三极管,那就可以通过继电器或 三极管控制外部大功率电路的通断。 最基本的输入功能是检测外部输入电平,如把 GPIO 引脚连接到按键,通过电平高低区分按键是 否被按下。
这是GPIO 硬件结构框图,就可以从整体上深入了解 GPIO 外设及它的各种应用模式。
1.GPIO口的工作模式
(1)、4种输入模式
(1)GPIO_Mode_IN_FLOATING 浮空输入
(2)GPIO_Mode_IPU 上拉输入
(3)GPIO_Mode_IPD 下拉输入
(4)GPIO_Mode_AIN 模拟输入
(2)、4种输出模式
(5)GPIO_Mode_Out_OD 开漏输出
(6)GPIO_Mode_AF_OD 复用开漏输出
(7)GPIO_Mode_Out_PP 推挽输出
(8)GPIO_Mode_AF_PP 复用推挽输出
(3)、4种最大输出速度
(1)2MHZ (低速)
(2)25MHZ (中速)
(3)50MHZ (快速)
(4)100MHZ (高速)
以下为这些模式进行简单的解析:
1.1 输入模式 (上拉/下拉/浮空)
在输入模式时,施密特触发器打开,输出被禁止。数据寄存器每隔 1 个 AHB1 时钟周期更新一 次,可通过输入数据寄存器 GPIOx_IDR 读取 I/O 状态。其中 AHB1 的时钟如按默认配置一般为 180MHz。 用于输入模式时,可设置为上拉、下拉或浮空模式。
1.2 输出模式 (推挽/开漏,上拉/下拉)
在输出模式中,输出使能,推挽模式时双 MOS 管以方式工作,输出数据寄存器 GPIOx_ODR 可 控制 I/O 输出高低电平。开漏模式时,只有 N-MOS 管工作,输出数据寄存器可控制 I/O 输出高 阻态或低电平。输出速度可配置,有 2MHz25MHz50MHz100MHz 的选项。此处的输出速度即 I/O 支持的高低电平状态最高切换频率,支持的频率越高,功耗越大,如果功耗要求不严格,把速度 设置成最大即可。 此时施密特触发器是打开的,即输入可用,通过输入数据寄存器 GPIOx_IDR 可读取 I/O 的实际 状态。
用于输出模式时,可使用上拉、下拉模式或浮空模式。但此时由于输出模式时引脚电平会受到 ODR 寄存器影响,而 ODR 寄存器对应引脚的位为 0,即引脚初始化后默认输出低电平,所以在 这种情况下,上拉只起到小幅提高输出电流能力,但不会影响引脚的默认状态。
1.3 复用功能 (推挽/开漏,上拉/下拉)
复用功能模式中,输出使能,输出速度可配置,可工作在开漏及推挽模式,但是输出信号源于其 它外设,输出数据寄存器 GPIOx_ODR 无效;输入可用,通过输入数据寄存器可获取 I/O 实际状 态,但一般直接用外设的寄存器来获取该数据信号。 用于复用功能时,可使用上拉、下拉模式或浮空模式。同输出模式,在这种情况下,初始化后引 脚默认输出低电平,上拉只起到小幅提高输出电流能力,但不会影响引脚的默认状态。
1.4模拟输入输出模式
模拟输入输出模式中,双 MOS 管结构被关闭,施密特触发器停用,上/下拉也被禁止。其它外设 通过模拟通道进行输入输出。 通过对 GPIO 寄存器写入不同的参数,就可以改变 GPIO 的应用模式,再强调一下,要了解具 体寄存器时一定要查阅《STM32F4xx 参考手册》中对应外设的寄存器说明。在 GPIO 外设中, 通过设置“模式寄存器 GPIOx_MODER”可配置 GPIO 的输入/输出/复用/模拟模式,“输出类型 寄存器 GPIOx_OTYPER”配置推挽/开漏模式,配置“输出速度寄存器 GPIOx_OSPEEDR”可选 2/25/50/100MHz 输出速度,“上/下拉寄存器 GPIOx_PUPDR”可配置上拉/下拉/浮空模式。
2、实践:使用寄存器点亮LED灯
2.1 下载程序软件keil5 uVision5
2.2 在STM32开发板上使用寄存器来点亮LED灯是一种常见的做法。
下面是一个简单的示例,展示如何通过配置寄存器来控制STM32开发板上的GPIO引脚以点亮LED灯。
下面是一个使用寄存器来点亮LED灯的示例代码(以CMSIS标准库为例):
#include "stm32f4xx.h"
int main(void) {
// 使能GPIOA时钟
RCC->AHB1ENR |= RCC_AHB1ENR_GPIOAEN;
// 配置PA5引脚为推挽输出
GPIOA->MODER |= GPIO_MODER_MODER5_0;
GPIOA->MODER &= ~GPIO_MODER_MODER5_1;
while (1) {
// 点亮LED
GPIOA->BSRRL = GPIO_BSRR_BS_5;
// 延时
for (int i = 0; i < 1000000; i++);
// 熄灭LED
GPIOA->BSRRH = GPIO_BSRR_BR_5;
// 延时
for (int i = 0; i < 1000000; i++);
}
}
如果你需要LED展示不同的花样,你可以参考以下代码:
首先,初始化GPIO时钟
想要只有红灯亮,就要关闭另外两个灯
当按下key1是红灯,按下key2是绿灯,同时按下key1和key2是蓝灯,代码如下:
————————————————整体代码为:
#include "stm32F4xx.h"
#include "stm32f4xx_conf.h"
#include "stdio.h"
void delay(uint32_t ms)
{
for(;ms!=0;ms--);
}
int main(void)
{
GPIO_InitTypeDef gpio_info;
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOH,ENABLE);
gpio_info.GPIO_Mode = GPIO_Mode_OUT;
gpio_info.GPIO_OType = GPIO_OType_PP;
gpio_info.GPIO_Pin = GPIO_Pin_10|GPIO_Pin_11|GPIO_Pin_12;
gpio_info.GPIO_PuPd = GPIO_PuPd_UP;
gpio_info.GPIO_Speed = GPIO_Low_Speed;
GPIO_Init(GPIOH,&gpio_info);
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOA,ENABLE);
gpio_info.GPIO_Mode = GPIO_Mode_IN;
gpio_info.GPIO_OType = GPIO_OType_PP;
gpio_info.GPIO_Pin = GPIO_Pin_0;
gpio_info.GPIO_PuPd = GPIO_PuPd_NOPULL;
gpio_info.GPIO_Speed = GPIO_Low_Speed;
GPIO_Init(GPIOA,&gpio_info);
RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOC,ENABLE);
gpio_info.GPIO_Mode = GPIO_Mode_IN;
gpio_info.GPIO_OType = GPIO_OType_PP;
gpio_info.GPIO_Pin = GPIO_Pin_13;
gpio_info.GPIO_PuPd = GPIO_PuPd_NOPULL;
gpio_info.GPIO_Speed = GPIO_Low_Speed;
GPIO_Init(GPIOC,&gpio_info);
GPIO_ResetBits(GPIOH,GPIO_Pin_11|GPIO_Pin_12);
while(1)
{
uint8_t key1=GPIO_ReadInputDataBit(GPIOA,GPIO_Pin_0);
uint8_t key2=GPIO_ReadInputDataBit(GPIOC,GPIO_Pin_13);
if (key1 == 1)
{
GPIO_ResetBits(GPIOH,GPIO_Pin_10);//µãÁÁºìµÆ
}
else
{
GPIO_SetBits(GPIOH,GPIO_Pin_10);//ϨÃðºìµÆ
}
if (key2 == 1)
{
GPIO_ResetBits(GPIOH,GPIO_Pin_11);//µãÁÁÂ̵Æ
}
else
{
GPIO_SetBits(GPIOH,GPIO_Pin_11);//ϨÃðÂ̵Æ
}
if (key1 == 1 && key2 == 1)
{
GPIO_SetBits(GPIOH,GPIO_Pin_10);//ϨÃðºìµÆ
GPIO_SetBits(GPIOH,GPIO_Pin_11);//ϨÃðÂ̵Æ
delay(0xFFFFFF);
GPIO_ResetBits(GPIOH,GPIO_Pin_12);//µãÁÁÀ¶µÆ
}
else
{
GPIO_SetBits(GPIOH,GPIO_Pin_12);//ϨÃðÀ¶µÆ
}
}
}
2.3下载验证
把编译好的程序下载到开发板并复位,可看到板子上的 LED 红灯被点亮。
通过操作寄存器,可以实现对STM32外设的控制。希望本文能帮助您了解STM32开发,并享受嵌入式系统带来的乐趣和挑战,有错误的地方欢迎大家指点。
版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
原文链接:https://blog.csdn.net/weixin_45479529/article/details/127846571