首页 > 其他分享 >GPIO

GPIO

时间:2025-01-14 15:11:43浏览次数:1  
标签:输出 IO 寄存器 GPIO uint32 CRL

GPIO

1. 基本定义和概念

IO复用:同一个IO引脚具备多个不同的功能;

IO重映射:当出现功能引脚冲突时,讲功能移动到到备用引脚上;

通用和复用的区别:通用表示直接控制,复用表示其他功能模块托管(片上外设)使用;

通用输入输出(GPIO,General Purpose Input/Output): 具有八种各种模式。分别是:

(1)输入浮空(Input floating)

(2)输入上拉(Input pull-up)

(3)输入下拉(Input-pull-down)

(4)模拟输入(Analog)

(5)通用开漏输出(Output open-drain)

(6)通用推挽式输出(Output push-pull)

(7)推挽式复用功能(Alternate function push-pull)

(8)开漏复用功能(Alternate function open-drain)

输出模式下:控制端口输出高低电平,用于驱动LED,蜂鸣器等,大功率器件借助驱动芯片间接控制。

输入模式下:读取端口的高低电平,用于读取按键,外接模拟信号的输入,ADC电压采集,模拟通信协议接收数据等。

IO输出最大速度:电压上升和下降的时间限制了IO的输出速度(极限状态下电平稳定时间太短)。考虑到低功耗,实际使用通常取满足要求最小通信速度。限制电压在VSS~VDD范围内。

Snipaste_2025-01-11_15-21-01

GPIO每位的具体电路结构:

图片1

2.开漏输出和推挽输出

2.1 推挽输出和开漏输出的区别

一句话概括:推挽支持高低电平输出,开漏仅有低电平外加高阻态。同时开漏模式的上方的P-MOS始终关闭

Snipaste_2025-01-11_15-14-38

补充:https://www.cnblogs.com/yangyang13/p/18060487

如何控制P-MOS与N-MOS见随笔:

2.2 推挽输出和开漏输出的选择

使用推挽输出:

  1. 驱动能力要求较高;
  2. 高信号传输;
  3. 不需要共用信号线(如果有设备输出0,有设备输出1就会形成短路);

使用开漏输出:

  1. 多个设备共用信号线,线与;
  2. 不同电压系统之间的接口(通过上拉电阻改变电平);
  3. 需要外部上拉电阻来确定逻辑高电平;

2.3 输入上拉、输入下拉和输入浮空的区别

一句话概括:当引脚浮空时,上拉电阻提供默认高电压,下拉电阻提供默认低电压。浮空则处于不确定状态。

image-20250111162349375

3 输入模式

3.1保护二极管的作用

当I/O引脚电压大于VDD时,如上图位于I/O引脚与VDD之间形成导通,同理,当电压低于VSS时,下二极管导通,形成钳位。

image-20250113145507530

3.2 输入是如何判断高低电平的

通过施密特触发器(图中的肖特基是翻译错误)对信号进行波形整形,然后输入数据寄存器中。

image-20250113150222873

补充:模拟输入时关闭施密特触发器,信号直接输入到片上外设。

4. GPIO寄存器

每个GPIO端口有7个相关的寄存器:

  1. 2个32位配置寄存器(GPIOx_CRL,GPIOx_CRH),可读可写,Port Configuration Register Low/High,端口配置低/高寄存器, 用于控制IO端口输入输出模式,CRL控制低八位引脚,CRH控制高八位引脚,每位引脚由MODE和CNF控制,共4bit位。其中MODE控制是输出还是输入以及工作速度,CNF控制是否上下拉或浮空及模拟输入。

  2. 2个32位数据寄存器(GPIOx_IDR和GPIOx_ODR),输入只能读,输出可读可写,Port Input/Output Data Register,端口输入/输出寄存器, 控制IO端口具体输入和输出的值(0/1)。均只有低16位使用,高16位保留。

  3. 1个32位置位/复位寄存器(GPIOx_BSRR),只能写,Port bit set/reset register, 端口位设置/清除寄存器,可以设置ODR具体某位的值,低16位从0~15,置1时设置0~15端口输出1,高16位从16~32,置1时设置0~15端口输出0。

  4. 1个16位复位寄存器(GPIOx_BRR),只能写,端口位清除寄存器,可以将ODR具体某位的值复位为0,只有低16位使用,高16位保留。

  5. 1个32位锁定寄存器(GPIOx_LCKR),可读可写,端口配置锁定寄存器,可以锁定寄存器的工作模式让其不被修改。使用方法比较特殊如下图
    image-20250114145552901

I/O端口位的基本结构(辅助理解寄存器功能):
image-20250114142136684

5. 实践验证

5.1 寄存器形式

实现逻辑:

​ 查找对应寄存器地址,改变其值到对应模式。以GPIOA_Pin_0为例,

  1. 配置时钟

    在存储映像的寄存器组起始地址进行查询
    image-20250114094647517

    查询可以看到,IO外设是位于APB2总线上,APB2ENR地址偏移量是0x18

    image-20250114095337512

    image-20250114100457471

    所以 APB2ENR地址为:0x4002 1000 + 0x18 ,因为GPIOA位于第二位,所以启动GPIOA时钟代码为: *(uint32_t *)(0x40021000 + 0x18) = 4;

  2. 配置IO输出模式寄存器

    查询对应寄存器组基地址

    image-20250114100029610

    查看对应偏移地址和寄存器参数功能

    image-20250114101430411

    image-20250114101030300

    参考上图,配置PA0为通用推挽输出代码为:*(uint32_t *)(0x4001 0800 + 0x00) = 3;

  3. 配置输出寄存器
    image-20250114103113878
    参考上图,配置PA0为输出0代码为:*(uint32_t *)(0x4001 0800 + 0xch) = 0xfffe;

  4. 优化,在"stm32f10x.h"头文件中已经定义了相关寄存器和结构体,可以直接调用。
    如下:

    #define PERIPH_BASE           ((uint32_t)0x40000000) /*!< Peripheral base address in the alias region */
    #define AHBPERIPH_BASE        (PERIPH_BASE + 0x20000)
    #define RCC_BASE              (AHBPERIPH_BASE + 0x1000)
    #define RCC                 ((RCC_TypeDef *) RCC_BASE)
    typedef struct
    {
      __IO uint32_t CR;
      __IO uint32_t CFGR;
      __IO uint32_t CIR;
      __IO uint32_t APB2RSTR;
      __IO uint32_t APB1RSTR;
      __IO uint32_t AHBENR;
      __IO uint32_t APB2ENR;
      __IO uint32_t APB1ENR;
      __IO uint32_t BDCR;
      __IO uint32_t CSR;
    
    #ifdef STM32F10X_CL  
      __IO uint32_t AHBRSTR;
      __IO uint32_t CFGR2;
    #endif /* STM32F10X_CL */ 
    
    #if defined (STM32F10X_LD_VL) || defined (STM32F10X_MD_VL) || defined (STM32F10X_HD_VL)   
      uint32_t RESERVED0;
      __IO uint32_t CFGR2;
    #endif /* STM32F10X_LD_VL || STM32F10X_MD_VL || STM32F10X_HD_VL */ 
    } RCC_TypeDef;	// 结构体内排序与芯片手册寄存器位置偏移量相对应,利用了结构体内地址连续的特点
    
    // 代码可优化为
        RCC->APB2ENR = 4;
        GPIOA->CRL = 3;
        GPIOA->ODR = 0xfffe;
    // 位操作优化
    	RCC->APB2ENR |= 0x1 << 2;
    	GPIOA->CRL &= ~(0x1 << 3);
        GPIOA->CRL &= ~(0x1 << 2);
        GPIOA->CRL |= 0x1 << 1;
        GPIOA->CRL |= 0x1 << 0;
        GPIOA->ODR &= ~(0x1 << 0);
    // "stm32f10x.h"头文件中也定义了对应寄存器的控制,再次优化
    #define  RCC_APB2ENR_IOPAEN                  ((uint32_t)0x00000004)         /*!< I/O port A clock enable */
    #define  GPIO_CRL_CNF0_0                     ((uint32_t)0x00000004)        /*!< Bit 0 */
    #define  GPIO_CRL_CNF0_1                     ((uint32_t)0x00000008)        /*!< Bit 1 */
    #define  GPIO_CRL_MODE0_0                    ((uint32_t)0x00000001)        /*!< Bit 0 */
    #define  GPIO_CRL_MODE0_1                    ((uint32_t)0x00000002)        /*!< Bit 1 */
    
    // 最终代码
        RCC->APB2ENR |= RCC_APB2ENR_IOPAEN;
    
        GPIOA->CRL &= ~GPIO_CRL_CNF0_1;
        GPIOA->CRL &= ~GPIO_CRL_CNF0_0;
        GPIOA->CRL |= GPIO_CRL_MODE0_1;
        GPIOA->CRL |= GPIO_CRL_MODE0_0;
    
        GPIOA->ODR &= ~GPIO_ODR_ODR0;
    

5.2 库函数形式

实现逻辑:

​ 使用cubeMX配置引脚状态,然后再通过keil在工程中调用Hal库函数实现想要的现象

  1. cubeMX配置关键界面
    image-20250114135517434
  2. 配置完后生成工程,我们可以发现,工程中会自动初始时钟配置和GPIO配置
    image-20250114140835655
  3. 在初始化函数中会配置时钟和GPIO
    image-20250114141017489
  4. 主函数中利用HAL_GPIO_WritePin函数进行IO端口的控制,请对应传入参数入如下值
    image-20250114141155085

标签:输出,IO,寄存器,GPIO,uint32,CRL
From: https://www.cnblogs.com/yangyang13/p/18670797

相关文章

  • 树莓派-11-GPIO的应用之开关实验
    文章目录1GPIO编码方式2RPI.GPIO2.1PWM2.2静态函数2.3DATA3开关实验3.1按键开关实验3.2倾斜开关实验3.3震动开关实验3.4迷你磁簧开关实验4附录4.1异常及解决4.2参考资料1GPIO编码方式wiringPi和BCM和BOARD编码树莓派上提供......
  • 树莓派-5-GPIO的应用实验之GPIO的编码方式和SDK介绍
    文章目录1GPIO编码方式1.1管脚信息1.2使用场合1.3I2C总线1.4SPI总线2RPI.GPIO2.1PWM脉冲宽度调制2.2静态函数2.2.1函数setmode()2.2.2函数setup()2.2.3函数output()2.2.4函数input()2.2.5捕捉引脚的电平改变2.2.5.1函数wait_for_e......
  • STM32MP157AAA开发板通过GPIO实现模拟I2C驱动获取光照,红外,接近传感器的数据
    实验目标:硬件:STM32MP157AAA开发板+拓展板管脚:拓展板光照,红外,接近传感器(AP3216C)I2C1_SCL对应核心板PF14,I2C1_SDA对应核心板PF15,可知从机地址为0X1E。梳理:I2C各信号下SCL与SDA的机制可查看STM32MP157AAA开发板通过GPIO实现模拟I2C驱动获取温湿度传感器数据-CSDN博客光照,红......
  • STM32MP157AAA开发板通过GPIO模拟SPI驱动通信控制数码管
    实验目标:硬件:STM32MP157AAA开发板+拓展板管脚:拓展板上数码管(M74HC595),由下图可知,数码管通过SPI与核心板通信,时钟(S)CK对应PE12、主机输出从机输入(MOSI)对应PE14、主机输入从机输出(MISO)对应PE13、从设备选择(CSN)对应PE11,由于当前电路SPI只有一个从设备,因此在硬件层面上将PE11常置为......
  • GPIO的八种工作模式(非原创)
    前言GPIO是通用输入输出端口(GeneralPurposeInputOutput)的简称,可以通过把GPIO引脚与外部设备连接起来,从而实现与外部通讯、控制以及数据采集的功能。最基本的输出功能是控制引脚输出高、低电平,实现开关控制等最基本的输入功能是检测外部输入电平等。其中有八种输入输出模......
  • 【WiFi】QCA6174A根据GPIO加载不同bdwlan文件修改实现
    QCA6174ADesignedtodeliveracost-effectiveWi-Fi/Bluetoothcombosolution,theQualcomm®QCA6174ASoC(System-on-Chip)isanintegrated,single-chipsolutioninasmallformfactorformobileandconsumerelectronicsapplications.QCA6174Asupp......
  • 2、蓝牙打印机点灯-GPIO输出控制
    1、硬件1.1、看原理图初始状态位高电平.需要驱动PA1输出高低电平控制PA1.1.2、看手册a、系统架构图GPIOA在APB2总线上。b、RCC使能GPIOA在第2位。c、GPIO寄存器配置端口:PA1模式:通用推挽输出模式--输出0、1即可速度:50M---芯片的最高频率是72M,输出高低电平......
  • 点风扇!手把手教你控制OrangePi3B的GPIO
    直接说结果用gpiosetgpio022=1来开启风扇,gpiosetgpio022=0可以关闭风扇。(需要sudo)确定GPIO接口买了OrangePi3B来当服务器,贴了挺大的一块散热片,但是负载高的时候还是会容易卡,会有几分钟SSH都连不上。正好外壳上有个可以安装风扇的孔。淘宝上卖的比较多的是一种使用插针的......
  • GPIO引脚配置
    #include"led.h"//初始化PA8和PD2为输出口.并使能这两个口的时钟        //LEDIO初始化voidLED_Init(void){  GPIO_InitTypeDef GPIO_InitStructure;     RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA|RCC_APB2Periph_GPIOD,ENABLE);  ......
  • 【AI8051U】第五节 - GPIO中断
    【草履虫也想学会】AI8051U-五-GPIO中断一.前言二.AI8051U的中断资源中断的相关概念中断仲裁NVICAI8051U中断资源:三.GPIO中断什么是GPIO中断GPIO中断相关寄存器GPIO中断优先级GPIO中断使能GPIO中断请求GPIO中断模式GPIO掉电唤醒中断四.GPIO中断运用GPIO中断配置中......