【stm32】swjtu西南交大嵌入式实验三 外部中断实验:按键中断

项目源文件:https://download.csdn.net/download/qq_61814350/89222788?spm=1001.2014.3001.5501 

实验内容:

1、编写程序,设置主程序:跑马灯以 0.2s 的速度旋转;将 KB1 设置为外部中断,下 降沿触发,按下 KB1 则全彩灯的 R 灯闪烁 5 次。编译、下载程序到开发板,观察实 验现象;按下 KB1,观察实验现象。

2、编写程序,设置主程序:跑马灯以 0.2s 的速度旋转;将 KB1,KB2 设置为外部中断, 下降沿触发,按下 KB1 则 R 闪烁 5 次,按下 KB2 则 G 闪烁 5 次。编译、下载程序到 开发板,观察实验现象;分别先后按下 KB1、KB2,观察实验现象。

3、设置主程序:跑马灯以 0.2s 的速度旋转;将 KB1,KB2 设置为外部中断,下降沿触 发,按下 KB1 则 R 闪烁 5 次,按下 KB2 则 G 闪烁 5 次,设置 KB1 外部中断抢占先优 先级设置为 1,KB2 外部中断抢占先优先级设置为 2。编译、下载程序到开发板,先 按下 KB2,G 在闪烁过程中,再按下 KB1,观察实验现象。

4、设置 KB1 和 KB2 外部中断的抢占先优先级均为 1,KB1 外部中断的响应优先级为 1, KB2 外部中断响应优先级为 2。实验时先按下 KB2,LED1 在闪烁过程中,再按下 KB1, 观察实验现象。 

5、用短线连接 PE0 和 PE1,当 KB1 和 KB2 外部中断优先级设置不一致,按下 KB1 或 KB2 时,观察实验现象。

6、应用设计: 主程序为 RGB 循环点亮,外部中断 KB1,蜂鸣器播放门铃音,外部中断 KB2,电机顺 时针旋转开门;KB2 的优先级高于 KB1。

按键及外部中断输入口配置

6b534a6ed7274955b1d30ff458c78e2c.png

注意:该实验使用的是按键外部中断,涉及到按键就有抖动,这是个大坑......

使用CubeMX创建工程

 这里只说明按键(PE0、PE1)外部中断的配置:下降沿触发。按下为低电平故内部上拉。

cc0dd299cf734fc08d053fd0d29a5326.png

RCC和SYS和前面的实验相同。

这里要配置NVIC:

 将对应的外部中断通道的优先级设置成对应的数字,左是抢占,右边是响应优先级。

注意:如果要在中断程序里用hal_delay要把下面的定时器中断的抢占优先级设为比两个外部中断的优先级高

0c1621c5502745f9804ab82315a8ad0f.png

时钟树配置:

00079d7d783440448ea169447eae2bc7.png

2c5a9687c1fd413694b0f25116bb809c.png

在project manager里面勾选上面的选项,可以把代码分开成c和h文件,看起来更清楚。

生成代码,可以进行查看:

 先看gpio.c,setpriority配置外部中断的优先级,这里为了方便,前几个实验不重复建立工程,我直接在这里修改了代码,以修改优先级。这个函数的参数先是抢占,然后是响应

99ff3a9cac8841b999481c621763ba6b.png

stm32f1xx_it.c里两个外部中断线的中断处理函数:

edbfcaa932ea4f2e943a247793c73109.png 查看他们都调用的这个函数:

45d900dd12d64cd693cdba078bb973ca.png

在这个函数里面,先确定这个中断是否被挂起,挂起就清除标志位,调用回调函数,这个回调函数是我们需要自己重写,实现自己的功能的函数。 

2f37a642226f42cabe0da453091cca8d.png

可以在main.c里面重写:

 根据不同的引脚来判断是哪个中断,做不同的处理:

void Light_TOGGLE(GPIO_Pin)
{
   HAL_GPIO_WritePin(GPIOB,GPIO_Pin,0);
	 for(int k=0;k<2400000;k++);
	 HAL_GPIO_WritePin(GPIOB,GPIO_Pin,1);
	 for(int k=0;k<2400000;k++);
}

void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
{
  //HAL_Delay(10);
  switch(GPIO_Pin)
	{
	  case KB1_Pin:for(int i=0;i<5;i++) Light_TOGGLE(L_RED_Pin);
		   break;
			//if(HAL_GPIO_ReadPin(KB1_GPIO_Port,KB1_Pin)==0){}
			 
		case KB2_Pin:for(int i=0;i<5;i++)  Light_TOGGLE(L_GREEN_Pin);
			break;
		//	if(HAL_GPIO_ReadPin(KB2_GPIO_Port,KB2_Pin)==0){}
			
	}
	
}

这里有个非常容易出错的地方,花了很久来排查。

在注释掉的地方,我是用来按键消抖的,思路是先延时一下,然后再确认按键是否为低电平,为低电平才做操作,这是很常见的一种消抖做法。但是,中断操作里面,灯的闪烁本身时间就很长了,处理完中断程序之后这个按键的抖动已经停止了,根本不用再消抖了。

这样导致做两个相同抢占优先级的按键中断实验的时候,比如第二个实验抢占都为3的时候,我先按KB1,在KB1对应的红灯闪烁时按下KB2,不会打断当前的中断,这是对的,但是当前的红灯闪烁五次,中断执行完毕后,就看不到绿灯闪烁了。但是按道理,绿灯中断应该排队在后面,红灯闪烁完他应该闪烁绿灯的。而问题就在这里,灯的闪烁本身时间就很长了,当你执行完红灯的中断之后,KB2的抖动都消失了,虽然它执行了KB2的中断程序,但是这个if判断为真时才执行灯闪烁的操作:

if(HAL_GPIO_ReadPin(KB2_GPIO_Port,KB2_Pin)==0){}

 此时KB2已经恢复成没被按下的样子,那么他肯定不会做绿灯闪烁的操作了。去除掉这个消抖的部分,就会看到绿灯排在后面闪烁了。

另外还有一个需要注意的地方,就是这样写,会发现红灯中断会执行两次,也就是,闪烁10次,

这里就需要修改之前所看到的调用回调函数的HAL_GPIO_EXTI_IRQHandler的内部,在这里面它先清掉标志位,再调用回调函数;这会导致按键的抖动又重新把标志位置位,又触发中断,于是需要调换一下两个语句的位置,也就是:

d6a1cb364ba04707938defae270e9177.png

先做完处理再清除标志位,这样按键抖动就不会影响了。所以,涉及到按键的外部中断需要特别处理这里的顺序,另外用CubeMX重新生成代码后,这里会恢复成原来的样子,要记得改。

如果还不明白,可以看下面视频的7.2节,

【【7.2】外部中断示例EXTI方式检测按键——Kevin带你读《STM32Cube高效开发教程基础篇》】 https://www.bilibili.com/video/BV1m8411L7eR/?share_source=copy_web&vd_source=9332b8fc5ea8d349a54c3989f6189fd3

再说一下第六个实验的电机(蜂鸣器前面实验已做过,不再赘述): 

dd1e0d9a467e4c60bc4e45dbd9ba785d.png

这个电机只要在电机两端,IA和IB加上不相同的电平,就能实现旋转,10或01,它们对应的旋转方向不同。

比如(先旋转一会儿再恢复静止):

void Rotate_Machine()
{
  HAL_GPIO_WritePin(GPIOD,GPIO_PIN_13,1);
	HAL_GPIO_WritePin(GPIOD,GPIO_PIN_12,0);
	
	for(int k=0;k<5000000;k++);
	HAL_GPIO_WritePin(GPIOD,GPIO_PIN_13,0);
	HAL_GPIO_WritePin(GPIOD,GPIO_PIN_12,0);
}

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

如若内容造成侵权/违法违规/事实不符,请联系我们进行投诉反馈qq邮箱809451989@qq.com,一经查实,立即删除!

相关文章

在ubuntu 24.04 上安装vmware workstation 17.5.1

ubuntu安装在新组装的i9 14900机器上&#xff0c;用来学习笨叔的ARM64体系结构编程&#xff0c;也熟悉Linux的用法。但有时候写文档总是不方便&#xff0c;还是需要window来用。因此想在ubuntu 24.04上安装Linux版本的vmware worksation 17.5.1以虚拟机的方式安装windows 11。其…

【软测学习笔记】测试入门Day03

&#x1f31f;博主主页&#xff1a;我是一只海绵派大星 &#x1f4da;专栏分类&#xff1a;软件测试笔记 &#x1f4da;参考教程&#xff1a;黑马教程❤️感谢大家点赞&#x1f44d;收藏⭐评论✍️ 目录 一、缺陷 1、定义 2、缺陷标准 3、缺陷产生的原因 4、缺陷的生命周…

Leetcode—1329. 将矩阵按对角线排序【中等】(unordered_map、priority_queue)

2024每日刷题&#xff08;121&#xff09; Leetcode—1329. 将矩阵按对角线排序 实现代码 class Solution { public:vector<vector<int>> diagonalSort(vector<vector<int>>& mat) {const int m mat.size();const int n mat[0].size();unorder…

指导网友完成一起Linux服务器系统文件删除导致不能启动情况下的数据恢复案例

昨日有网友在微信群发起救助&#xff0c;Linux系统不能启动&#xff0c;使用救援U盘也无法恢复&#xff0c;协助他进行了数据恢复&#xff0c;本文记录了处置过程。 图片为网友提供&#xff0c;照得歪歪扭扭的&#xff0c;将就着看看吧。 一、问题现象 1、报错信息 Linux服…

335GB,台北地区倾斜摄影OSGB数据V0.2版介绍!

前几天发布了台北地区倾斜摄影OSGB数据第一个版本(139GB,台北倾斜摄影OSGB数据V0.1版),虽然数据还是一个半成品&#xff0c;完全没想到热度很高&#xff0c;很多读者对这份数据都有比较浓厚的兴趣&#xff0c;在这里首先感谢各位读者的大力支持与鼓励&#xff0c;给了我持续更新…

Discuz! X系列版本安装包

源码下载地址&#xff1a;Discuz! X系列版本安装包 很多新老站长跟我说要找Discuz! X以前的版本安装包&#xff0c;我们做Discuz! X开发已经十几年了&#xff0c;这些都是官方原版安装包&#xff0c;方便大家使用&#xff08;在官网已经找不到这些版本的安装包了&#xff09; …

NLP发展及其详解

一、RNN(循环神经网络) 在这里附上一个很好的笔记 零基础入门深度学习(5) - 循环神经网络 RNN(循环神经网络)的结构特点在于其循环单元的设计,这种设计允许网络在处理序列数据时保持对之前信息的记忆。下面详细解释RNN的结构: 循环单元:RNN的循环单元是网络的核心,它…

4.Docker本地镜像发布至阿里云仓库、私有仓库、DockerHub

文章目录 0、镜像的生成方法1、本地镜像发布到阿里云仓库2、本地镜像发布到私有仓库3、本地镜像发布到Docker Hub仓库 Docker仓库是集中存放镜像的地方&#xff0c;分为公共仓库和私有仓库。 注册服务器是存放仓库的具体服务器&#xff0c;一个注册服务器上可以有多个仓库&…

Shell脚本入门:编写自动化任务的利器

一、Shell概述 Shell最早产生于20世纪70年代早期的Unix操作系统中。作为一种命令解释器&#xff0c;它位于操作系统的最外层&#xff0c;负责直接与用户进行交互。Shell把用户的输入解释给操作系统&#xff0c;并处理操作系统的输出结果&#xff0c;然后将其反馈给用户。这种交…

你不需要总是在 React 中使用 useState

在我审查的一个拉取请求中&#xff0c;我注意到在许多拉取请求中看到的一种模式。React 组件具有多个 UI 状态&#xff0c;例如 loading、error 和 success。 作者使用了多个 useState 钩子来管理这些状态&#xff0c;这导致代码难以阅读且容易出错&#xff0c;例如&#xff1a…

java案例-读取xml文件

需求 导入依赖 <dependencies><!-- dom4j --><dependency><groupId>dom4j</groupId><artifactId>dom4j</artifactId><version>1.6.1</version></dependency> </dependencies>代码 SAXReader saxReade…

九_进程关系1+1-终端设备

在Linux操作系统中&#xff0c;/dev/tty、/dev/tty0和/dev/console是三个特殊的设备文件&#xff0c;它们在终端控制和输入/输出过程中扮演着重要的角色。尽管它们看起来很相似&#xff0c;但实际上它们之间存在一些重要的区别。本文将详细介绍这三个设备文件之间的区别以及它们…

支付宝沙盒(java使用支付宝)springboot

目录 前言 注册账号&#xff08;直接搜索支付宝沙盒&#xff09; ​编辑 具体代码编写 Application配置(按自己需求添加) config&#xff08;这里需要亲自添加appid&#xff0c;privateKey&#xff0c;publicKey&#xff09; controller类 Service类 ServiceImpl类 运…

编写你的第一个 golang 的应用程序

进行你的第一个golang的程序 当你把程序都安装好以后 环境变量配置 好 vscode 插件下载好以后 1. 创建一个test.go 的文件 //主包&#xff0c;可执行文件所在包 package main//导入包 import "fmt"//主函数&#xff0c;入口函数 func main() { }2.解释 需要导入包 …

前端入门:HTML(css轮廓,填充,宽高)

1.CSS轮廓 注意&#xff1a; outline中&#xff0c;out-style是必须要设置的&#xff0c;格式为&#xff1a; outline-style一共有以下的几个值&#xff1a; 2.CSS填充属性 这是一个用于在一个元素的内容周围产生空间&#xff0c;也就是边框内到白框外之间的距离&#xff0c;…

FPlan Part1 EP1(MySQL)

今天完成了MySQL的第一部分&#xff0c;计划分为三部分&#xff0c;预计将在五一假期前完成&#xff0c;以及一个Java小游戏。 重点如下

【MySQL 所遇问题】

【MySQL 所遇问题】 总结&#xff1a;Error Code: 1064.You have an error in your SQL syntax报错解释1&#xff1a;报错解释2处理过程 Error Code&#xff1a;1366 - Incorrect string value:报错解释处理过程 总结&#xff1a; Error Code: 1064 不可见字符。 某些文本处理…

java8 Stream流常用方法(持续更新中...)

java8 Stream流常用方法 1.过滤数据中年龄大于等于十八的学生2.获取对象中其中的一个字段并添加到集合(以学生姓名&#xff08;name&#xff09;为例)3.获取对象中其中的一个字段并转为其他数据类型最后添加到集合(以学生性别&#xff08;sex&#xff09;为例&#xff0c;将Str…

解析链动2+1模式:探寻电商新商业契机

大家好&#xff0c;我是微三云周丽 在当今数字化时代&#xff0c;电商行业日新月异&#xff0c;不断涌现出各种创新商业模式。其中&#xff0c;链动2121模式以其独特的商业逻辑和快速裂变的特性&#xff0c;吸引了众多用户和企业家的关注。本文将深入剖析链动2121模式的运作机…

在 Windows 系统上安装 TeamViewer 13

在 Windows 系统上安装 TeamViewer 13 References 默认安装到所有用户 同意协议 安装目录 勾选内容 打开文件位置 打开 rClientID.exe Extras -> Options -> Advanced Show advanced options -> Display language 重新启动TeamViewer 语言可修改为中文简体 …