当前位置: 首页 > article >正文

STM32_实验5_中断实验

通过外部中断来检测四个按键按下的状态:

WK_UP 控制蜂鸣器响和停

KEY0 控制 LED_R 互斥点亮

KEY1 控制 LED_G 互斥点亮

KEY2 控制 LED_B 互斥点亮。

中断的基本概念:

中断请求(IRQ):

        当发生某个特定事件(例如硬件信号、定时器溢出等)时,相关的外部或内部设备会向处理器发出中断请求。这种请求通知处理器有事情需要处理。

中断服务程序(ISR):

        当处理器接收到中断请求后,它会暂停当前的执行,保存当前的状态,并跳转到预先定义的中断服务程序(ISR)。ISR 是一段特定的代码,用于处理中断事件。

中断优先级:

        处理器可以为不同的中断分配不同的优先级,以决定在多个中断发生时,哪个中断首先得到处理。高优先级的中断会抢占低优先级的中断。

中断响应流程:

        中断触发:外部事件或内部条件触发中断请求。
        中断信号:处理器收到中断信号,暂停当前任务。
        保存状态:处理器保存当前执行状态,以便中断处理完成后能够恢复。
        执行 ISR:跳转到中断服务程序,处理具体的中断事件。
        恢复状态:中断处理完成后,恢复之前保存的状态,继续执行被中断的任务。

中断向量表:

        中断向量表是一个存储中断服务程序入口地址的表格。处理器通过查找中断向量表来找到并执行相应的 ISR。

中断的类型:

外部中断:

        外部中断(External Interrupt)指的是由外部事件触发的中断信号,用于处理来自微控制器外部的信号或事件。这种中断通常由外部硬件信号(如按钮、传感器或其他设备)产生,并被用于通知微控制器有重要事件需要处理。
        外部中断的配置通常涉及设置中断触发条件(例如边沿触发或电平触发)、中断优先级和使能中断请求。STM32 微控制器通过 EXTI(External Interrupt/Event Controller)模块来配置外部中断。
        外部中断广泛用于处理事件驱动任务,如按钮按下检测、外部信号捕获、时钟脉冲计数等。

 内部中断:

        由内部外设或系统模块产生的中断,如定时器溢出、USART 接收数据、ADC 转换完成等。

系统异常:

        处理器内的异常事件,如硬件故障、内存管理错误等。

在 STM32 微控制器中,中断的设置和使用通常包括以下步骤:

        配置外设或 GPIO:设置需要触发中断的外设或引脚。
        配置中断线:设置 EXTI 模块或其他中断控制器,指定中断源和触发条件。
        使能中断:在 NVIC 中使能相应的中断线,设置中断优先级。
        编写 ISR:实现中断服务程序来处理特定的中断事件。

例如,配置一个定时器中断:

// 定时器中断服务程序
void TIM1_UP_IRQHandler(void)
{
    if (TIM1->SR & TIM_SR_UIF)  // 检查更新中断标志
    {
        TIM1->SR &= ~TIM_SR_UIF; // 清除中断标志
        // 执行中断处理代码
    }
}
// 配置定时器并使能中断
void Timer_Init(void)
{
    // 初始化定时器
    // ...
    
    // 启用定时器中断
    HAL_NVIC_EnableIRQ(TIM1_UP_IRQn);
}

外部中断回调函数:

        在 STM32 HAL 库中,HAL_GPIO_EXTI_Callback 是外部中断回调函数的标准命名。这个命名是由 HAL 库规定的,用于处理 GPIO 外部中断的回调。如果你想使用这个回调函数,你需要在你的代码中实现它,并在其中定义当外部中断触发时的具体行为。

void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
{
    if (GPIO_Pin == GPIO_PIN_0)
    {
        // 处理引脚 0 的外部中断
    }
    else if (GPIO_Pin == GPIO_PIN_1)
    {
        // 处理引脚 1 的外部中断
    }
    // 其他引脚的处理
}

注意: 这个命名是为了确保与 HAL 库的兼容性和一致性。如果你在自定义项目中使用不同的命名,可能会影响到 HAL 库的功能调用。

HAL_GPIO_TogglePin 函数(高/低翻转):

HAL_GPIO_TogglePin 是 STM32 HAL 库中的一个函数,用于翻转(切换)指定 GPIO 引脚的状态。这意味着,如果引脚当前的电平是高(GPIO_PIN_SET),函数会将其切换为低(GPIO_PIN_RESET);如果电平是低,函数则会将其切换为高。

函数原型:

void HAL_GPIO_TogglePin(GPIO_TypeDef* GPIOx, uint16_t GPIO_Pin);

参数: 

GPIOx      :指定 GPIO 端口。例如:GPIOA, GPIOB, GPIOC 等。这个参数决定了要操作哪个                           GPIO端口。
GPIO_Pin :指定要操作的 GPIO 引脚。可以是以下形式的掩码:GPIO_PIN_0, GPIO_PIN_1,                      GPIO_PIN_2, ..., GPIO_PIN_n(n 是引脚编号),或者多个引脚的位掩码组合,例                         如GPIO_PIN_0 | GPIO_PIN_1。 

作用是将指定的 GPIO 引脚的状态从高电平翻转为低电平,或从低电平翻转为高电平。这对于需要周期性切换引脚状态的应用非常有用,例如控制 LED 的闪烁。

 实验开始:

1.  具体的 pgio 引脚配置如下,蜂鸣器和 RGB 灯和以前一样配置,按键 KEY0(PD10) 、KEY1(PD9)、KEY2(PD8) 、WK_UP(PC13) 配置外部中断模式。配置串口 1 用于调试。

2、将按键 KEY0(PD10) 、KEY1(PD9)、KEY2(PD8) 配置为下降沿触发的外部中断模式,按键 WK_UP(PC13) 配置为上升沿触发的外部中断模式。这里举例为按键 WK_UP(PC13) 配置为上升沿触发的外部中断模式。

NVIC 使能中断线路组

(配置完生成代码)

EXTI (External Interrupt) line [9:5] 是 STM32 微控制器中的一个外部中断线路组,用于处理 GPIO 引脚 5 到 9 的外部中断请求。这一组中的每一条中断线都可以连接到对应的 GPIO 引脚,当引脚的电平发生变化时,触发相应的中断服务程序(ISR)。

3、在 HAL 库中,中断运行完后会先进入相对应的中断回调函数,处理完该函数后,才会退出中断。我们一般将中断需要处理代码会放在中断回调函数中去运行。

中断回调函数:void HAL_GPIO_EXTI_Callback*(uint16_t GPIO_Pin);

这里在 main.c 里可以定义 void HAL_GPIO_EXTI_Callback*(uint16_t GPIO_Pin); 函数编写逻辑代码,完成本实验。主函数可以空置,只需等待中断触发外部中断回调函数即可。

/* USER CODE BEGIN 4 */
// 外部中断回调函数
void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
{
    switch (GPIO_Pin)
    {
        case GPIO_PIN_8: // KEY2
            HAL_GPIO_TogglePin(GPIOE, GPIO_PIN_9);
            printf("LED_B state transition\n");
            break;
        case GPIO_PIN_9: // KEY1
            HAL_GPIO_TogglePin(GPIOE, GPIO_PIN_8);
            printf("LED_G state transition\n");
            break;
        case GPIO_PIN_10: // KEY0
            HAL_GPIO_TogglePin(GPIOE, GPIO_PIN_7);
            printf("LED_R state transition\n");
            break;
        case GPIO_PIN_13: // WK_UP
            HAL_GPIO_TogglePin(GPIOB, GPIO_PIN_2);
            printf("beep state transition\n");
            break;
        default:
            break;
    }
}
/* USER CODE END 4 */

中断优先级的配置
在 STM32 中,中断优先级通常分为两个部分:

        抢占优先级(Preemption Priority): 决定了中断之间的优先处理顺序。抢占优先级高的中断可以打断抢占优先级低的中断。
        响应优先级(Sub Priority): 决定了具有相同抢占优先级的中断的处理顺序。

 通过以下函数可以设置中断优先级:

HAL_NVIC_SetPriority(IRQn_Type IRQn, uint32_t PreemptPriority, uint32_t SubPriority);

 示例:配置中断优先级

假设有三个中断源,分别是 EXTI0、EXTI1 和 EXTI2。我们希望 EXTI0 拥有最高的优先级,EXTI1 次之,EXTI2 优先级最低。可以通过以下代码设置:

// 设置 EXTI0 中断优先级为最高(抢占优先级 0,响应优先级 0)
HAL_NVIC_SetPriority(EXTI0_IRQn, 0, 0);
HAL_NVIC_EnableIRQ(EXTI0_IRQn);
// 设置 EXTI1 中断优先级为次高(抢占优先级 1,响应优先级 0)
HAL_NVIC_SetPriority(EXTI1_IRQn, 1, 0);
HAL_NVIC_EnableIRQ(EXTI1_IRQn);
// 设置 EXTI2 中断优先级为最低(抢占优先级 2,响应优先级 0)
HAL_NVIC_SetPriority(EXTI2_IRQn, 2, 0);
HAL_NVIC_EnableIRQ(EXTI2_IRQn);


http://www.kler.cn/news/356237.html

相关文章:

  • 记录 ruoyi-vue-plus在linux 部署遇到的问题
  • 实现对redis过期键监听案例
  • TikTok广告账号被封?常见原因及解决方法分享
  • 快速创建一个vue项目并运行
  • 【Spring】Cookie和Session是什么
  • 企业级调度器 LVS
  • vue $nextTick 实现原理
  • traceroute 命令输出解释
  • uniapp上如何绑定全局事件总线(引入自定义全局组件例如弹窗)
  • Java中的Object类
  • 前端将cvs格式数据导出为Excel表
  • uniapp配置微信小程序分包(分包优化)
  • 代码随想录算法day43 | 图论part01 | 图论理论基础,深搜理论基础,98. 所有可达路径,广搜理论基础
  • 确保Spring Boot定时任务只执行一次方案
  • Git原理与使用(一)
  • 在Windows上搭建ChatTTS:从本地部署到远程AI音频生成全攻略
  • Realistic Car Controller Pro 车辆汽车控制
  • 软件设计模式------抽象工厂模式
  • 电脑桌面自己变成了英文Desktop,怎么改回中文
  • c语言求π的值