STM32:GPIO输入输出

news2024/11/23 13:47:37

文章目录

  • 1、GPIO介绍
    • 1.1 GPIO的基本结构
    • 1.1 GPIO的位结构
  • 2、 GPIO工作模式
  • 3、GPIO标准外设库接口函数
    • 3.1 RCC接口函数
    • 3.2 GPIO接口函数
      • 3.2.1 GPIO的读取函数
      • 3.2.1 GPIO的写入函数
  • 4、GPIO的初始化

1、GPIO介绍

GPIO(General Purpose Input Output)通用输入输出口,也就是我们平时所说的I/O口

  • 可配置为8种输入输出模式。
  • 引脚电平:0v~3v,部分引脚可容忍为5v。
  • 输出模式下可控制端口输出高低电平,用以驱动LED、控制蜂鸣器、模拟通信协议输出时序等。
  • 输入模式下可读取端口的高低电平或电压,用于读取按键输入、外接模块电平信号输入、ADC电压采集、模拟通信协议接受数据等。

1.1 GPIO的基本结构

在这里插入图片描述
在STM32中,所有的GPIO都是挂载在APB2外设总线上的;其中GPIO所有的外设名称都是按照GPIOA、GPIOB、GPIOC等等这样来命名的。

每个GPIO外设总共有16个引脚,编号是0~15;例如GPIOA的第0号引脚,我们一般将其称之为PA0。

在每个GPIO模块内,主要包含了寄存器和驱动器。寄存器就是一段特殊的存储器,内核可以通过APB2总线对寄存器进行读写,这样来完成输出电平和读取电平的功能。

寄存器的每一位对应一个引脚,其中输出寄存器写1,对应的引脚就会输出高电平;写0,就输出低电平。输入寄存器读取为1,就证明对应的端口目前是高电平;读取为0,就是低电平。

STM32是32位的单片机,所有STM32内部寄存器都是32位的,但这个端口只有16位,因此这个寄存器只有低16位对应有端口,而高16位是没有被用到的。

驱动器主要是用来增加信号的驱动能力,寄存器只负责存储数据,若要进行点灯的操作,还是需要驱动器来负责增大驱动能力的。

1.1 GPIO的位结构

在这里插入图片描述
最右边的I/O引脚,接了两个保护二极管来对输入电压限幅。

上面的二极管VDD-3.3V,下面二极管接VSS-0V:

  • 如果输入电压比3.3V还要高,那上方这个二极管就会导通。
  • 输入电压产生的电流就会直接流入VDD而不会流入内部电路,这样就可以避免过高的电压对内部这些电路产生伤害。
  • 如果输入电压比0V还要低,这个电压是相对于VSS的电压,所以是可以有负电压的,这是下方的二极管就会导通,电流会从VSS直接流到I/O出去,而不会从内部电路汲取电流,也可以保护内部电路。
  • 如果输入电压在0~3.3V之间,那两个二极管均不会导通。

左上方一个上拉电阻,一个下拉电阻

  • 目的是为了提供一个默认的输入电平,因为对应一个数字的端口,输入的不是高电平就是低电平,如果输入引脚什么都不接,那到底是算高电平还是低电平。
  • 实际情况是,如果输入引脚啥都不接,这时输入就会处于一种浮空的状态,引脚的输入电平极易受外界干扰而改变。
  • 为了避免引脚悬空导致的输入数据不确定,我们就需要在这里加上上拉或者下拉电阻了。
  • 此时,如果接入上拉电阻,当引脚悬空时,还有上拉电阻来保证引脚的高电平,所以上拉输入又可以称作是默认为高电平的输入模式。

上拉电阻至VDD,下拉电阻至VSS,这个开关是可以通过程序进行配置的:

  • 如果上边断开,下边开关关闭,为下拉模式,反之为上拉模式。
  • 如果两个都断开,就是浮空输入模式

施密特触发器:

  • 他的作用是对输入电压进行整形。
  • 如果输入电压大于某一阈值,输出就会瞬间升为高电平。
  • 如果输入电压小于某一阈值,输出就会瞬间降为低电平。

输入数据寄存器:

  • 用程序读取输入数据寄存器对应某一位的数据,就可以知道端口的输入电平。

上面还有两路线路,这些就是连接到片上外设的一些端口:

  • 模拟输入:连接到ADC上的,因为ADC需要接受模拟量,所以这根线是接到施密特触发器前面的。
  • 复用功能输入:这个是连接到其他需要读取端口的外设上的,比如串口的输入引脚等,这根线接收的是数字量,所以在施密特触发器后面。

2、 GPIO工作模式

通过配置GPIO的端口配置寄存器,端口可以配置位以下8种输入输出模式:

(1)浮空输入

引脚内部既不接上拉电阻也不接下拉电阻,直接经施密特触发器输入I/O引脚的信号。可以读取到引脚电平,若引脚悬空,则电平不确定。

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

引脚内部连接上拉电阻,通过开关连接到电源VDD,可读取引脚电平,引脚悬空默认为高电平。

(3)下拉输入(Input Pull-down)
与上拉输入模式相反,内部连接下拉电阻,引脚悬空默认为低电平。

(4)模拟输入

GPIO无效,引脚直接接入内部ADC,实现对外部信号的采集。

(5)开漏输出(Open-Drain,OD)

可输出引脚电平,高电平为高阻态,低电平接Vss。

(6)推挽输出(Push-Pull,PP)

可输出引脚电平,高电平接VDD,低电平接Vss。

(7)复用开漏输出(AF-OD)

由片上外设控制,高电平为高阻态,低电平接Vss。

(8)复用推挽输出(AF-PP)

由片上外设控制,高电平为接VDD,低电平接Vss。

3、GPIO标准外设库接口函数

3.1 RCC接口函数

在这里插入图片描述

我们可以在Library文件中找到rcc.h这个文件,其中里面我们最常用到的就是红框内的3个函数:

	RCC APB外设时钟控制、RCC APB2外设时钟控制、RCC APB1外设时钟控制

其中上面常用的3个函数的操作方法都是一样的,第一个参数选择外设,第二个参数选择使能或失能。

3.2 GPIO接口函数

在这里插入图片描述

上图就是GPIO的全部库函数,其中红色方框内的函数用来实现读写GPIO口的功能,基本上常用的就是上面蓝色方框内的函数。

1.GPIO_DeInit,调用这个函数后,所指定的GPIO外设就会被复位。

2.GPIO_AFIODeInit,也是一样,可以复位AFIO外设。

3.GPIO_Init,用结构体的参数来初始化GPIO口。我们需要先定义一个结构体变量,然后再给结构体赋值,最后调用这个函数,这个函数内部就会自动读取结构体的值,然后自动把外设的各个参数配置好。这种Init函数在STM32中基本所有的外设都有,一般我们初始化外设都是使用这个Init函数来完成的。

4.GPIO_StructInit,这个函数可以把结构体变量赋一个默认值。

3.2.1 GPIO的读取函数

1.uint8_t GPIO_ReadInputDataBit,用来读取输入寄存器的某一个端口的输入值,参数是GPIOx和GPIO_Pin,用来指定某一个端口,返回值是uint8_t,代表这个端口的高低电平。

2.uint16_t GPIO_ReadInputData,读取整个输入寄存器,参数只有一个GPIOx,用来指定外设,返回值是uint16_t,一个16位的数据,每一位代表一个端口值。

3.uint8_t GPIO_ReadOutputDataBit,读取输出寄存器的某一个位,因此他并不是用来读取端口的输入数据的,一般用于输出模式下,用来查询字节输出的是什么。

4uint16_t GPIO_ReadOutputData,用来读取整个输出寄存器。

总结来说:若想读取GPIO口的话,需要用到ReadIput的这两个函数;若在输出模式下,想要看一下现在输出了什么,才需要用到ReadOutput这两个函数。

3.2.1 GPIO的写入函数

1.GPIO_SetBits,可以把指定的端口设置为高电平。

2.GPIO_ResetBits,可以把指定的端口设置为低电平。

3.GPIO_WriteBit,这个函数有三个参数,前两个也是指定端口;第三个是BitValue,可以根据第三个参数的值来设置指定的端口。

4.GPIO_Write,第一个参数GPIOx选择外设;PortValue,这个函数可以同时对16个端口进行写入操作。

4、GPIO的初始化

操作STM32的GPIO总共需要3个步骤,涉及了RCC和GPIO两个外设:

  • 使用RCC开启GPIO的时钟;
  • 使用GPIO_Init函数初始化GPIO;
  • 使用输入或输出函数控制GPIO口。

当我们需要控制一个LED的亮灭时,我们要先对GPIO端口进行初始化

例如我们需要点亮PA0口的LED,首先新建一个LED.c的工程,用来存放LED驱动程序的主题代码,将我们所需要初始化的函数写入这个工程文件中。

首先我们需要调用的是RCC里面的APB2外设时钟控制函数:
在这里插入图片描述

跳转到定义后查看参数说明,他的第一个参数就应该为RCC_APB2Periph_GPIOA,第二个参数就为ENABLE,这样时钟就开启了。

接着调用GPIO_Init函数,跳转定义查询后可以写出第一个参数为GPIOA,第二个参数是一个结构体,我们先给第二个参数结构体重命名为GPIO_InitStructure,如下所示:

#include "stm32f10x.h"                  // Device header
void LED_Init(void)
{
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE); //开启时钟
	GPIO_InitTypeDef GPIO_InitStructure;//配置端口模式
	
	GPIO_Init(GPIOA,&GPIO_InitStructure);
}

接着我们通过结构体成员操作符“.”来引出结构体成员,如下所示:

GPIO_InitStructure.GPIO_Mode = ;
GPIO_InitStructure.GPIO_Pin = ;
GPIO_InitStructure.GPIO_Speed = ;

接着再配置其中所需要的参数,最后的初始化代码如下:

#include "stm32f10x.h"                  // Device header
void LED_Init(void)
{
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE); //开启时钟
	GPIO_InitTypeDef GPIO_InitStructure;//配置端口模式
	GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Pin=GPIO_Pin_0;
	GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;
	GPIO_Init(GPIOA,&GPIO_InitStructure);
}

当我们完成GPIO初始化后,写入主函数下载后就可以查看LED灯的变化。

上电后LED处于低电平状态,因此为常亮;若想上电为高电平,即LED熄灭的状态则在初始化函数后添加一个写入函数GPIO_SetBits即可。程序如下:

#include "stm32f10x.h"                  // Device header
void LED_Init(void)
{
	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOA,ENABLE); //开启时钟
	GPIO_InitTypeDef GPIO_InitStructure;//配置端口模式
	GPIO_InitStructure.GPIO_Mode=GPIO_Mode_Out_PP;
	GPIO_InitStructure.GPIO_Pin=GPIO_Pin_0;
	GPIO_InitStructure.GPIO_Speed=GPIO_Speed_50MHz;
	GPIO_Init(GPIOA,&GPIO_InitStructure);
	
	GPIO_SetBits(GPIOA,GPIO_Pin_0);
}

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

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

相关文章

【MQTT】服务端、客户端工具使用记录

目录 一、服务端 1.1 下载 1.2 相关命令 (1)启动 (2)关闭 (3)修改用户名和密码 1.3 后台管理 (1)MQTT配置 (2)集群概览 (3)…

场外期权个股怎么对冲?

今天期权懂带你了解场外期权个股怎么对冲?场外个股期权是一种在非交易所市场进行的期权交易,它允许投资者针对特定的股票获得未来买入或卖出的权利。 场外期权个股怎么对冲? 持有相反方向的期权:这是最直接的对冲方法&#xff0c…

今晚 19:00 | 从这两个问题入手,带你了解数据要素相关税务问题

五一假期已经结束,返工后当然是继续劳动啦~数据要素系列直播《星光对话》第三期也将在今晚19:00,继续跟大家见面。 本期直播,依然由 星光数智咨询总监 刘靖 主讲,带来:《数据要素相关税务问题解读》。 主要围绕两个问题…

怎么快速分享视频文件?用二维码看视频的方法

怎样不通过传输下载分享视频内容呢?以前分享视频内容,大多会通过微信、QQ、邮箱、网盘等形式来传递。但是这种方式需要下载后才可以观看,不仅占用手机内存,而且效率也比较低,所以现在很多人会采用视频生成二维码的方式…

为 Flutter 应用设置主题:ThemeData 和 ColorScheme 指南

在媒体和其他来源中有许多关于这个主题的文章,那么这篇文章的必要性是什么? 在本文中,我计划仅关注 ThemeData 小部件的关键点以及我的开发经验中最常用的参数,并且您将获得有关每个参数如何对您的应用程序执行操作的简要说明。 …

LeetCode70:爬楼梯

题目描述 假设你正在爬楼梯。需要 n 阶你才能到达楼顶。 每次你可以爬 1 或 2 个台阶。你有多少种不同的方法可以爬到楼顶呢? 解题思想 1.确定dp数组以及下标的含义 dp[i]: 爬到第i层楼梯,有dp[i]种方法 2.确定递推公式 从dp[i]的定义可以…

旋转测径仪的常见故障和排除方法

关键字: 旋转测径仪,测径仪常见故障,测径仪故障排除方法,测径仪维护,测径仪较零 点击 “开始测量”按钮时提示“初始化失败!”无法进行测量。 ◆ 检查控制柜面板“工作”指示灯(绿)是否点亮; ◆ 最小化软件窗口,查看…

解密某游戏的数据加密

前言 最近有个兄弟通过我的视频号加我,咨询能否将这个dubo游戏游戏开始前就将数据拿到从而进行押注,于是通过抓包工具测试了下,发现数据有时候是明文,有时候确实密文,大致看了下有这几种加密:Md5aes、Md5&a…

用Pycharm对图片中表格进行文字识别,并导出到xlsx文件中

需要使用到百度API对图片文字进行识别 在百度智能云官网中注册一个账号百度智能云-登录https://login.bce.baidu.com/ 之后在管理中心里创建应用 创建完成后会得到: 记下一下AppID&API Key&Secret Key这三个值,调用接口时使用。 示例图片&…

字符编码(十六进制)

题目描述 假设一个简易的变长编码规则XUTF:每个字符有一个唯一编号值 unicodeVal(如汉字“华”的编号十进制值是21326),使用1~6个字节进行编码,编码规则如下: 编码格式: 编号值范围编码后字节长度n二进制格式(x 表示有效位,其它为固定位)[0, 2^7)1字节1xxxxxxx[2^7,…

数智算网,链启未来 | 算力网络子链诚邀各方加入

4月28日,在中国移动算力网络大会期间,由中国移动集团主办,中国移动研究院和云能力中心联合承办的“数智算网,链启未来”共链行动算力网络专场会议成功召开。中国移动研究院副院长段晓东,中国移动集团首席专家、云能力中…

Tomcat、MySQL、Redis最大支持说明

文章目录 一、Tomcat二、MySQL三、Redis1、最大连接数2、TPS、QPS3、key和value最大支持 一、Tomcat 查看SpringBoot内置Tomcat的源码,如下: 主要就是看抽象类AbstractEndpoint,可以看到默认的核心线程数10,最大线程数200 通过…

百元挂耳式耳机哪款好?五款高品质一流机型不容错过

开放式耳机以其独特的不入耳设计,大大提升了佩戴的舒适度。相较于传统的入耳式耳机,它巧妙地避免了对耳朵的压迫,降低了中耳炎等潜在风险。不仅如此,开放式耳机还能让你保持对周边声音的灵敏度,无论是户外跑步还是骑行…

umount.nfs : /out:device is busy

-f, --force force unmount (in case of an unreachable NFS system) -l, --lazy detach the filesystem now, and cleanup all later-l 这么牛?现在分离文件系统,稍后再进行清理

【实战】采用jenkins pipeline实现自动构建并部署至k8s

文章目录 前言部署jenkins编写docker-compose-jenkins.yaml配置maven源启动jenkins解锁jenkins Jenkins默认插件及git、镜像仓库、k8s凭证配置host key verification configuration修改为不验证Gitee ssh阿里云镜像仓库ssh编写pipeline安装以下常用插件将kubectl命令文件拷贝到…

Google Pixel4手机刷机+Root+逆向环境详细教程

Google Pixel4手机刷机Root逆向环境配置详细教程 刷机工具下载 Windows10、Google Pixel4手机当前安卓10系统、adb工具、要刷的谷歌原生的Android11最新刷机包、安装google usb驱动、美版临时twrp-3.6.0_11-0-flame.img和美版永久twrp-installer-3.6.0_11-0-flame.zip、Magis…

前端组件库之ant-design-vue

在这里记录一个这个组件库我之前没有发现最近才发现的一个很好用的功能(应该叫功能吧?) 就是 这个flex弹性布局,之前在开发时,一直使用elementUI,是第一次使用这个组件库,所以没有发现这个功能这么好用 你…

适合宝妈的项目,一单20,看似不起眼的小生意,却能闷声发财!

向大家推荐一个小项目,信息差较大,每单至少有20元的利润。目前参与的人还不多,是个不错的机会。操作方法也非常简单,只需利用京东家政券赚取差价。可能很多人是第一次了解到这个——京东竟然还有家政券。 周周近财:让…

线下订单平台操作步揍

收款管理 1微信收款查询 1. 获取微信数据 获取微信数据。通过时间范围 查找微信数据调用第三方接口如下: Map map HttpPost.doPost("https://qyapi.weixin.qq.com/cgi-bin/externalpay/get_bill_list?access_token"ApiUtils.getWxtoken(),args); 其中…

[YOLOv8] 用YOLOv8实现指针式圆形仪表智能读数(二)

最近研究了一个项目,利用python代码实现指针式圆形仪表的自动读数,并将读数结果进行输出,若需要完整数据集和源代码可以私信。 目录 🍓🍓1.yolov8实现圆盘形仪表智能读数 🙋🙋2.表盘指针语义…