为什么我的中断被调用,但不会进入处理程序?

Why does my interrupt get called, but won't enter the handler?

我正在尝试以中断模式接收来自 USART 的通信。调试器告诉我在按键时调用了中断,但执行卡在向量 table 定义中。

我使用以下代码初始化我的 usart。

static void MX_USART2_UART_Init(void)
{
  huart2.Instance = USART2;
  huart2.Init.BaudRate = 19200;
  huart2.Init.WordLength = UART_WORDLENGTH_8B;
  huart2.Init.StopBits = UART_STOPBITS_1;
  huart2.Init.Parity = UART_PARITY_NONE;
  huart2.Init.Mode = UART_MODE_TX_RX;
  huart2.Init.HwFlowCtl = UART_HWCONTROL_NONE;
  huart2.Init.OverSampling = UART_OVERSAMPLING_16;
  if (HAL_UART_Init(&huart2) != HAL_OK)
  {
    Error_Handler();
  }

  /* USER CODE END USART2_Init 2 */
  LED_Initialize();
  USART2->CR1=USART_CR1_RE|USART_CR1_TE|USART_CR1_UE|USART_CR1_RXNEIE; // Enable interrupt
  NVIC_SetPriority(USART2_IRQn, 2); // set priority level
  NVIC_EnableIRQ(USART2_IRQn); // Enable in NVIC
}


void USART2_IRQHandler(void)
{
    blink_led();
}

如果我 运行 应用程序处于调试模式,按下一个键,停止并逐步执行代码,我发现它在此处的分支指令上循环,在包含的 startup_stm32f446xx.s 内。

USART2_IRQHandler
        B USART2_IRQHandler
        PUBWEAK USART3_IRQHandler
        SECTION .text:CODE:REORDER:NOROOT(1)

所以我知道正在生成中断,但它似乎找不到我的处理程序。即使不在调试模式下,我的 LED 也不会闪烁,这是我单独测试过的功能。 我不确定这个问题是否来自 HAL 库。我已经阅读了他们的文档和变体以及他们的 NVIC 启用说明,结果相同。 usart 在轮询中工作正常,但我的功能需要中断。

你的问题有 "c++" 标签,所以我假设你用 C++ 编译器编译你的项目。 C++ 编译器 name-mangle 函数名,这会阻止分支指令找到它的目标,因为它的真实名称不再是 USART2_IRQHandler。

您需要在 ISR 前添加 extern "C" 以告诉 C++ 不要 name-mangle 它。

extern "C" void USART2_IRQHandler(void) {
    blink_led(); 
}