标签:区分 tag 端口配置 结构 eve its 数据 是什么 就是
1、GPIO简介
STM32F103ZET6有多个GPIO组,如GPIOA、GPIOB、GPIOC...等等。每个GPIO组具有16个IO口。
GPIO组的寄存器都是类似的,每个GPIO组都有2个32位的配置寄存器、2个32位的数据寄存器、1个32位的置位/复位寄存器、1个16位复位寄存器和1个32位锁定寄存器。
STM32的很多IO口都是5V兼容的,具体哪些IO口是5V兼容的,可以从芯片的数据手册管脚描述中查到,在手册的IO Level中标FT的就是5V电平兼容的。
2、GPIO配置
STM32F103ZET6可以通过配置寄存器CRH和CRL将IO配置成不同的功能。IO具有以下几种不同的模式:
CRH和CRL寄存器的每4个BIT用来配置一个IO的功能,CRL用来配置低8位IO的功能,CRH用来配置高8位IO的功能。
CNF1、CNF0、MODE1、MODE0这4个位组成了1个IO的配置位,如GPIOF0的配置位CNF1、CNF0、MODE1、MODE0这些位位于CRL寄存器中的BIT3~BIT0;GPIOF1的配置位CNF1、CNF0、MODE1、MODE0这些位位于CRL寄存器中的BIT7~BIT4;而GPIOF8的配置位CNF1、CNF0、MODE1、MODE0这些位位于CRH寄存器中的BIT3~BIT0;以此类推。CRH和CRL这两个寄存器总共有64个BIT,总共组成了16个IO的配置位。
IO口的配置表如下:
MODE1和MODE0是用来配置IO的输入、输出状态;CNF1和CNF0则是根据IO口的输入和输出状态的不同配置不同的IO功能。
在配置IO的时候,首先通过MODE1和MODE0配置IO是输入还是输出,再通过CNF1和CNF0配置IO是什么功能的输入或输出。
通过CNF1、CNF0、MODE1、MODE0这些位可以将IO设置成上拉/下拉输入,但是具体是设置成上拉输入还是下拉输入,并不是根据这4个位来决定的。IO口是通过ODR数据寄存器来区分到底是设置成上拉输入还是下拉输入。如果IO口的ODR被置为1,则IO口被设置为上拉输入;如果IO口的ODR被清为0,则IO口被设置为下拉输入。
CNF1、CNF0、MODE1、MODE0配置位功能如下:
MODE1和MODE0控制IO的输入和输出:
CNF1、CNF0则需要根据IO是输入还是输出来区分:
IO设置为输入时:
IO设置为输出时:
3、GPIO的复位状态
芯片在上电复位后,大部分IO口的模式默认为浮空输入模式。但是有些IO比较特殊,比如PA15、PA14、PA13、PB4、PB3等IO,这些IO是JTAG和SWIO调试下载口,芯片复位后,这些IO就被默认成了JTAG和SWIO等功能,也就是说芯片复位后,PA15、PA14、PA13、PB4、PB3等IO并不能通过常规的配置设置成相应的功能。如果需要使用这些口的IO口功能,则必须将这些IO功能重新映射为GPIO口。
需要注意的是如果将PA15、PA14、PA13、PB4、PB3等口重映射为GPIO口后,则不能用调试器调试程序,而且也不能下载程序,只有通过复位芯片,使这些IO口的功能处于复位默认功能,才能下载程序。
复位后,PA15、PA14、PA13、PB4、PB3这些引脚被配置成如下模式:
4、GPIO锁定机制
GPIO的锁定机制允许冻结IO口的配置。当在一个端口位上通过LCKR寄存器执行了锁定(LOCK)程序,在下一次复位之前,将不能再更改端口位的配置。
5、外设的GPIO配置
可以在中文参考手册的GPIO介绍章节查到外设的GPIO设置,比如说如果要使用USART_TX功能,需要将USART_TX脚位配置成什么状态,可以在参考手册中查到。
6、GPIO寄存器
CRH和CRL是GPIO的配置寄存器,用来配置IO的功能。
IDR是GPIO的输入数据寄存器。通过IDR寄存器可以读出IO的状态。需要注意的是IDR寄存器只能以字(16位)的形式读出。
ODR是GPIO的输出数据寄存器。通过ODR寄存器可以输出高低电平。
BSRR是GPIO的端口位设置/清除寄存器。BSRR寄存器的高16位是清除IO位,低16位是置位IO位。需要注意的是BSRR只有在写入1的时候,相应的功能才有作用,写入0是无效的。
BRR是GPIO的端口位清除寄存器。BRR基础只有在写入1的时候,相应的功能才有作用,写入0无效。
LCKR是GPIO的端口配置锁定寄存器。LCKR寄存器用来锁定IO口的配置,设置后,除了复位后不能再配置IO的状态。
7、HAL库操作GPIO
以下面的程序为例说明:
void LED_Init(void)
{
GPIO_InitTypeDef GPIO_InitStruct;
__HAL_RCC_GPIOF_CLK_ENABLE();
GPIO_InitStruct.Pin = GPIO_PIN_6|GPIO_PIN_7|GPIO_PIN_8|GPIO_PIN_9;
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_HIGH;
HAL_GPIO_Init(GPIOF, &GPIO_InitStruct);
HAL_GPIO_WritePin(GPIOF, GPIO_PIN_6|GPIO_PIN_7|GPIO_PIN_8|GPIO_PIN_9, GPIO_PIN_RESET);
}
首先定义一个GPIO_InitTypeDef结构体。
在操作GPIO口之前,需要先使能GPIO的时钟。在HAL库中,是通过宏定义的方式使能或失能相应外设时钟的。一般在stm32f1xx_hal_rcc_ex.h文件当中。如果不知道某个外设的时钟是在哪个寄存器使能的,可以通过stm32f1xx_hal_rcc_ex.h查看对应的时钟使能程序。
HAL_GPIO_Init函数是GPIO初始化函数,通过传入的参数来配置IO的功能。
GPIO_InitStruct.Pin选择要设置的IO脚。
GPIO_InitStruct.Mode选择要设置的功能。
GPIO_InitStruct.Pull选择设置上拉或下拉或无上下拉。
GPIO_InitStruct.Speed选择设置IO口的速度。
在HAL库中GPIO的函数被封装在stm32f1xx_hal_gpio.c文件中,可以在该文件中查看每个函数是如何实现和使用的。
标签:区分 tag 端口配置 结构 eve its 数据 是什么 就是
原文地址:https://www.cnblogs.com/h1019384803/p/10987785.html