【STM32】GPIO

news2024/11/17 3:48:18

一、GPIO简介

1. 基本介绍

GPIO是通用输入输出端口的简称,STM32芯片通过GPIO与外设连接,从而实现与外设的数据收发。

  • 最基本的输出功能是由STM32控制引脚输出高、低电平,实现开关控制。如把GPIO引脚接入到LED灯控制LED亮灭,或者接入到三极管控制外部大功率电路的通断。
  • 最基本的输出功能是检测外部输入的高、低电平。如通过读取引脚的电平来区分按键是否被按下。
在这里插入图片描述

STM32的GPIO被分成了很多组/端口(Port),每个Port有16个引脚(Pin),如STM32F103ZET6芯片就有GPIOA~GPIOG 7个端口144个引脚,部分引脚除了作为GPIO使用之外,还有其它专用功能在复用。在这里插入图片描述

2. 工作模式

GPIO有8中工作模式,如图所示
在这里插入图片描述

浮空输入:由于没有接上拉电阻或下拉电阻,电平的高低完全取决于外部的输入,所以浮空输入电平极易受到外界的干扰,一般接按键会用到这个模式。

开漏输出等效电路如下图

在这里插入图片描述

  • 工作原理:Ug为高电平时,NMOS关闭,所以外部必须要接上拉电阻,此时OUT输出VDD电压,否则OUT既不输出高电平不输出低电平,为高阻态;Ug为低电平时,NMOS导通,OUT输出接地电压0V
  • 特性:开漏电路具有“线与”特性,即若有多个开漏模式的引脚连接到一起,只有所有都是高阻态时才会输出上来电阻电压,否则只要有一个引脚是低电平,整条线路都会输出低电平0V
  • 应用场景:一般应用在I2C、SMBUS通讯等需要“线与”的总线电路中,或者在驱动电平与输出电平不匹配的场景,如需要输出5V时,而由于STM32的GPIO引脚实际输出的是3.3V,此时就可以通过外部的上拉电阻来输出5V

推挽输出等效电路如下图

在这里插入图片描述

  • 工作原理:输出一个高电平经过反向器后,PMOS得到一个低电平后会导通,NMOS得到一个高电平后关闭,此时OUT对外输出高电平;输出一个低电平时经反相器后,PMOS关闭,NMOS导通,此时OUT对外输出一个低电平。
  • 特性:推挽输出高电平为3.3V,低电平为0V,当引脚高低电平切换时,两个MOS管轮流导通输出高低电平,提高了负载能力和开关速度。
  • 应用场景:一般应用在输出电平为0和3.3V高速切换开关状态的场合,STM32中,除了必须用开漏模式,一般更习惯用推挽输出模式。

3. 框图分析

在这里插入图片描述
1. 保护二极管

  • 两个二极管可以防止引脚外部输入过高或者过低的电压时,对芯片进行损坏,当引脚电压高于Vdd时上方二极管导通,电流不会进入芯片,当引脚电压低于Vss即负电压时下方二极管导通,电路不会吸取芯片的电流。以此防止不正常电压引入芯片导致芯片烧毁。
  • 即便如此,引脚也不可以直接驱动大功率器件时,如直接用引脚驱动电机,要么芯片烧毁,要么电机不转。

2. 输入、输出驱动器

  • 输入驱动器
    • 上拉电阻和下拉电阻,作用通俗来讲就是赋初值,当两个开关都是断开时就是浮空输入,
    • TTL肖特基触发器,作用就是将输入的模拟电压转为高低电平,如果要读取模拟数据,则不需要经过TTL肖特基触发器。
  • 输出驱动器。电路通过反向P-MOS和反向N-MOS,来实现了推挽输出和开漏输出两种模式。
    • 推挽输出:此时两个MOS管都会工作,控制输出高电平时,PMOS导通,NMOS关闭,电路输出Vdd电平;控制输出低电平时,PMOS关闭,NMOS导通,电路输出Vss电平。
    • 开漏输出:此时PMOS是无效的,只有NMOS工作。控制输出高电平时,电路为高阻态不输出电平,要想获取电平只能靠GPIO外部的电源;控制输出低电平时,NMOS导通,电路输出Vss电平

3. 输出数据寄存器

  • 通过写程序来设置输出数据寄存器GPIOx_ODR的值,以此来实现输出控制高低电平image-20230630232227368

  • 置位/复位寄存器GPIOx_BSRR可以通过修改输出数据寄存器的值来影响电路的输出

在这里插入图片描述

4. 复用功能输出

image-20230630233140463

  • GPIO的引脚除了当作STM32芯片的通用IO口使用之外,还有其它片上外设也可以对其进行控制,即为了减少引脚的数量而对引脚进行了复用,通过输出控制前的选择器来选择数据来源于输出数据寄存器还是片上外设
  • 如进行串口通信,需要进行数据发送时,就可以将UARTx_TX对应的GPIO引脚配置成USART串口复用功能,然后通过该引脚发送数据

5. 输入数据寄存器:就是将肖特基触发器转换后的0/1数字信号,存储到输入数据寄存器中GPIOx_IDR中,通过读取该寄存器就可以知道该该GPIO引脚的电平image-20230630234404716

6. 复用功能输入与复用功能输出类似,不多介绍

7. 模拟输入:一般用于ADC采集电压,此时信号不经过肖特基触发器,从而得到ADC外设采集到的原始模拟信号

4. 寄存器

GPIO配置寄存器:GPIO的每个端口都有2个对应的端口配置寄存器,端口上的每个引脚需要4位来进行配置,因此每个寄存器只能配置8个引脚,所以每个端口的16个引脚需要2个寄存器来配置。

image-20230701000214610

image-20230701000237663

  • 输入模式:肖特基触发器打开,可以通过GPIOx_IDR寄存器读取IO状态,此时GPIOx_ODR无效。
  • 推挽/开漏输出模式:推挽输出时双MOS管都工作,开漏输出时只有NMOS工作,可以同GPIOx_ODR寄存器输出高低电平,此时输出速度配置的越高功耗越大。输出模式时,肖特基触发器是打开的,所以即便是输出模式也可以通过GPIOx_IDR读取IO的实际状态。
  • 复用推挽/开漏输出:复用功能模式时可以配置输出使能和速度,此时GPIOx_ODR无效,但可以通过GPIOx_IDR寄存器读取IO状态,一般直接用外设寄存器来获取。

端口输入数据寄存器

image-20230701002027308

端口输出数据寄存器

image-20230701002052365

端口位设置/清除寄存器

image-20230701002107920

二、程序示例

1. GPIO输出——点亮LED

1.1 原理图

  • LED_R/G/B分别与GPIO的PB5/0/1相连
  • LED共阳极,因此当GPIO输出低电平时LED点亮,高电平LED灭

image-20230701002936381

1.2 配置寄存器

控制LED为输出

  • GPIOB_CRL的[MODE0/1/5]配置为输出模式,最大速度50MHz(此处对最大速度无要求,随便选一个即可)
  • GPIOB_CRL的[CNF0/1/5]配置为通用推挽输出模式

控制LED灯亮

  • GPIOB_ODR的[ODR0/1/5]配置为0,或者对GPIOB_BSRR的[BR0/1/5]置1并且对[BS0/1/5]清0

控制LED灯灭

  • GPIOB_ODR的[ODR0/1/5]配置为1,或者对GPIOB_BSRR的[BS0/1/5]置1

1.3 程序示例

/* --------------------bsp_gpio_led.h--------------------- */
/* 自定义数据结构 */
#define LED_PORT		GPIOB

typedef enum
{
	LED_R = GPIO_Pin_5,
	LED_G = GPIO_Pin_0,	
	LED_B = GPIO_Pin_1,	
}LED_Typedef;

/* -------------------bsp_gpio_led.c--------------------- */
void GPIO_LED_Config(void)
{
	GPIO_InitTypeDef GPIO_InitStruct;
	GPIO_InitStruct.GPIO_Pin  	= LED_R;
	GPIO_InitStruct.GPIO_Speed 	= GPIO_Speed_2MHz;
	GPIO_InitStruct.GPIO_Mode 	= GPIO_Mode_Out_PP;

	
	GPIO_Init(LED_PORT, &GPIO_InitStruct);
}

void GPIO_LED_On(LED_Typedef LED_Type)
{
	GPIO_ResetBits(LED_PORT, (uint16_t)LED_Type);
}
void GPIO_LED_Off(LED_Typedef LED_Type)
{
	GPIO_SetBits(LED_PORT, (uint16_t)LED_Type);
}

2. GPIO输入——检测按键

2.1 原理图

在这里插入图片描述

  • 由于下拉GND的存在,当松开按键时,PA0和PC13引脚读取到低电平
  • 按下按键时,3V3导通,PA0和PC13读取到高电平

2.2 数据手册

在这里插入图片描述

2.3 示例代码

/* --------------------bsp_gpio_key.h--------------------- */
#define KEY1_PORT		GPIOA
#define KEY2_PORT		GPIOC

typedef enum
{
	KEY1 = GPIO_Pin_0,
	KEY2 = GPIO_Pin_13
}KEYNum_Typedef;

typedef enum
{
	Key_Relase,
	Key_Press
}KEYStatus_Typedef;

/* --------------------bsp_gpio_key.c--------------------- */
void GPIO_KEY_Config(void)
{
	GPIO_InitTypeDef GPIO_InitStruct;
	GPIO_InitStruct.GPIO_Pin  	= KEY1;
  	GPIO_InitStruct.GPIO_Mode 	= GPIO_Mode_IN_FLOATING;

	GPIO_Init(KEY1_PORT, &GPIO_InitStruct);
}

/* 返回指定按键的状态 */
KEYStatus_Typedef GPIO_KEY_Status(KEYNum_Typedef KEYNum)
{
	KEYStatus_Typedef ret_status;
	if(KEYNum == KEY1)			
		ret_status = GPIO_ReadInputDataBit(KEY1_PORT, KEYNum);
	else			
		ret_status = GPIO_ReadInputDataBit(KEY2_PORT, KEYNum);
		
	return ret_status;
}


本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/727525.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

中小企业的必然选择——构建高效、安全的企业网络

在当今技术驱动的商业环境中,可靠且高效的企业网络对中小型企业的成功是至关重要的。随着对数据密集型应用的需求不断增加,无线网络技术随之迅速发展,企业必须构建一个更快、更安全的网络以保证业务安全稳定开展。本文重点讲解中小型企业网络…

常用stream方法记录

目录 过滤filter()获取最大最小值根据条件统计数量list转mapkey值唯一key值不唯一 distinct去重groupingBy分组map遍历取list中某元素组成新的listlist转数组String基本数据类型数组转换 数组转listArrays.asList()Collections.addAll基本数据类型数组转list 源码和…

阿里云绑定域名

在阿里云安全组与宝塔安全放开8081端口 server {listen 8081;server_name www.whxyyds.top;charset utf-8;location / {root /home/ruoyi/projects/ruoyi-ui;try_files $uri $uri/ /index.html;index index.html index.htm;}location /prod-api/ {proxy_set_header …

途乐证券|A股自动驾驶概念“夏日躁动”

进入7月以后,A股智能汽车产业链——尤其是自动驾驶板块,开始逐渐收复去年失地。 香港途乐证券有限公司(191883.com)是香港最优秀的股票投资平台,平台致力于为投资者提供专业、安全、诚信的股票策略服务,通过…

微信内置h5浏览器 getBrandWCPayRequest支付

目录 getBrandWCPayRequest支付 什么是getBrandWCPayRequest支付? 如何使用getBrandWCPayRequest支付? getBrandWCPayRequest支付的特点和优势 结论 WeixinJSBridge:微信浏览器的JavaScript桥接工具 WeixinJSBridge的作用 WeixinJSBri…

【震惊】Top1清华考研985考研专业课惨遭团灭!

原谅我今天用了个“UC的标题”,只是他真的太令我震惊了!(请本次事件受影响者,务必看到最后,我会给出我的建议) 事情的起因这样的:这周二有同学发我一条通知,清华大学通信考研考试科…

关于DBC文件的创建增加几点补充

上一节说了:DBC文件的简介与创建 这一节补充几点:关于DBC文件的创建增加几点补充 关于节点地址的定义和修改 有些朋友发现新建某个节点的时候,address栏的内容是灰色的,无法进行定义和修改 这个数值的更改不是在这里进行设置的…

18.ADC模数转换

1.STM32ADC简介: ADC(Analog to Digital Converter)即模数转换器,它可以将模拟信号转换成数字信号。按照其转换原理主要分为逐次逼近型、双积分型、电压频率转换型三种。 STM32 ADC主要特性: 12位分辨率;转换结束、注入…

Vue基础 -- 生命周期 数据共享

1 组件的生命周期 1.1 生命周期 & 生命周期函数 生命周期(Life Cycle)是指一个组件从创建 -> 运行 -> 销毁的整个阶段,强调的是一个时间段。 生命周期函数:是由 vue 框架提供的内置函数,会伴随着组件的生命…

UNI-APP_vmin横屏适配问题

vmax和vmin vmax 相对于视口的宽度或高度中较大的那个。其中最大的那个被均分为100单位的vmax vmin 相对于视口的宽度或高度中较小的那个。其中最小的那个被均分为100单位的vmin当竖屏布局时750rpx是竖屏布局屏幕的宽度 vmin不管横竖屏的情况下,100vmin都是手机屏幕…

Web漏洞-敏感信息泄露-Git操作

实验目的 熟悉常见git常见操作,如上传、回归、修改仓库等操作。 实验环境 git操作服务器,1台 web安全操作机,1台(可选) 实验内容 1.安装Git:sudo apt-get install git 2.安装Apache,为了模…

机器学习技术(二)——Python科学运算模块(Numpy、Pandas)

机器学习技术(二)——Python科学运算模块(Numpy、Pandas) 文章目录 机器学习技术(二)——Python科学运算模块(Numpy、Pandas)一、Numpy1、介绍、安装与导入2、Numpy常用操作 二、Pan…

Java面向对象程序开发——多线程开发

文章目录 前言多线程多线程的实现①、继承Thread类Thread常用方法Thread的构造器优缺点 ②、实现Runnable接口优缺点 ③、实现Callable接口Runnable接口和继承Thread类的区别 线程同步机制volatile同步锁 同步方法lock锁 线程池 前言 线程(thread)是一个程序内部的一条执行路径…

shared_ptr产生内存泄漏的场景

使用 shared_ptr 可以帮助管理动态分配的内存,它使用引用计数的方式来跟踪共享对象的引用数量,当引用计数为零时,会自动释放内存。然而,shared_ptr 也存在一些潜在的内存泄漏的场景,下面是一些常见的情况: …

LVS和keepa lived群集

keepa lived 简述 一.keepalived 服务重要功能 1管理LS负载均衡器软件 keepalived可以通过读取自身的配置文件,实现通过更底层的接口直接管理Lvs配置以及服务的启动 停止功能 这会使 LVS应用跟更加简便 2 支持故障自动切换 (failover) ①两台知己同时安装好kee…

网络字节序和套接字

4.1主机字节序列和网络字节序列 主机字节序列分为:大端字节序和小端字节序 大端:高位字节存储在内存的低地址处,低位字节存储在内存的高地址处。 小端:高位字节存储在内存的高地址处,低位字节存储在内存的低地址处。…

【算法基础】数据结构

链表 单链表 826. 单链表 - AcWing题库 #include<bits/stdc.h> using namespace std; const int N 100010; int m; int e[N],ne[N];//记录数据和下一结点坐标 int head,idx;//当前指向的结点 void init() {head-1;idx0; } void addtohead(int x) {e[idx]x;ne[idx]hea…

前端框架Vue

Vue 介绍 官方网站&#xff1a;https://cn.vuejs.org/ Vue.js是一种用于构建用户界面的开源JavaScript框架。它是一种轻量级的框架&#xff0c;易于学习和使用。它基于标准HTML&#xff0c;CSS和JavaScript构建&#xff0c;并提供了一套生声明式的&#xff0c;组件时的编程模…

【深入浅出 Spring Security(十三)】使用 JWT 进行前后端分离认证(附源码)

使用 JWT 进行前后端分离认证 一、JWT 的简单介绍二、使用 JWT 进行安全认证后端结合SpringSecurity实现前端Vue3结合Pinia、Axios实现测试结果 一、JWT 的简单介绍 JWT 全称 Java web Token&#xff0c;在此所讲述的是 JWT 用于身份认证&#xff0c;用服务器端生成的JWT去替代…

spring--Ioc控制反转/DI依赖注入

IOC控制反转-解耦 1.概念&#xff1a;在使用对象的时候&#xff0c;由主动的new转换为外部提供对象&#xff0c;将对象创建的控制权交给外部&#xff0c;即控制反转 2.spring提供了一个容器&#xff0c;称为IOC容器&#xff0c;用来从当ioc中的外部 3.被管理或者被创建的对象在…