stm32 HAL库学习笔记3——外部中断
CubeMX设置
GPIO设置
NVIC设置
中断处理函数
- stm32f4xx_it.c
void EXTI3_IRQHandler(void)
{
/* USER CODE BEGIN EXTI3_IRQn 0 */
/* USER CODE END EXTI3_IRQn 0 */
HAL_GPIO_EXTI_IRQHandler(GPIO_PIN_3);
/* USER CODE BEGIN EXTI3_IRQn 1 */
/* USER CODE END EXTI3_IRQn 1 */
}
- stm32f4xx_hal_gpio.c
/**
* @brief This function handles EXTI interrupt request.
* @param GPIO_Pin Specifies the pins connected EXTI line
* @retval None
*/
void HAL_GPIO_EXTI_IRQHandler(uint16_t GPIO_Pin)
{
/* EXTI line interrupt detected */
if(__HAL_GPIO_EXTI_GET_IT(GPIO_Pin) != RESET)
{
__HAL_GPIO_EXTI_CLEAR_IT(GPIO_Pin);
HAL_GPIO_EXTI_Callback(GPIO_Pin);
}
}
需要手动添加的代码
cubeMX会在stm32f4xx_it.c中生成中断处理函数,追踪代码会发现
__weak void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
空函数,需要用户在代码中声明覆盖掉这个回调函数, 如下我在main.c中添加的代码
尾部增加 `__HAL_GPIO_EXTI_CLEAR_IT(GPIO_Pin);清除中断标记,消除抖动造成的中断标记置位
/* USER CODE BEGIN 4 */
void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin)
{
HAL_Delay(20);
switch (GPIO_Pin) {
case GPIO_PIN_0:
if (HAL_GPIO_ReadPin(GPIOA, GPIO_PIN_0) == GPIO_PIN_SET) {
HAL_GPIO_TogglePin(GPIOF, GPIO_PIN_8);
}
break;
case GPIO_PIN_2:
if (HAL_GPIO_ReadPin(GPIOE, GPIO_PIN_2) == GPIO_PIN_RESET) {
HAL_GPIO_TogglePin(GPIOF, GPIO_PIN_9);
}
break;
case GPIO_PIN_3:
if (HAL_GPIO_ReadPin(GPIOE, GPIO_PIN_3) == GPIO_PIN_RESET) {
HAL_GPIO_TogglePin(GPIOF, GPIO_PIN_10);
}
break;
case GPIO_PIN_4:
if (HAL_GPIO_ReadPin(GPIOE, GPIO_PIN_4) == GPIO_PIN_RESET) {
HAL_GPIO_TogglePin(GPIOF, GPIO_PIN_8);
HAL_GPIO_TogglePin(GPIOF, GPIO_PIN_9);
}
break;
}
__HAL_GPIO_EXTI_CLEAR_IT(GPIO_Pin);
}
GPIO初使化
static void MX_GPIO_Init(void)
{
GPIO_InitTypeDef GPIO_InitStruct = {0};
/* GPIO Ports Clock Enable */
__HAL_RCC_GPIOE_CLK_ENABLE();
__HAL_RCC_GPIOC_CLK_ENABLE();
__HAL_RCC_GPIOF_CLK_ENABLE();
__HAL_RCC_GPIOH_CLK_ENABLE();
__HAL_RCC_GPIOA_CLK_ENABLE();
/*Configure GPIO pin Output Level */
HAL_GPIO_WritePin(GPIOF, GPIO_PIN_8|GPIO_PIN_9|GPIO_PIN_10, GPIO_PIN_RESET);
/*Configure GPIO pins : KEY2_Pin KEY1_Pin KEY0_Pin */
GPIO_InitStruct.Pin = KEY2_Pin|KEY1_Pin|KEY0_Pin;
GPIO_InitStruct.Mode = GPIO_MODE_IT_FALLING;
GPIO_InitStruct.Pull = GPIO_PULLUP;
HAL_GPIO_Init(GPIOE, &GPIO_InitStruct);
/*Configure GPIO pin : PF8 */
GPIO_InitStruct.Pin = GPIO_PIN_8;
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStruct.Pull = GPIO_PULLUP;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
HAL_GPIO_Init(GPIOF, &GPIO_InitStruct);
/*Configure GPIO pins : PF9 PF10 */
GPIO_InitStruct.Pin = GPIO_PIN_9|GPIO_PIN_10;
GPIO_InitStruct.Mode = GPIO_MODE_OUTPUT_PP;
GPIO_InitStruct.Pull = GPIO_NOPULL;
GPIO_InitStruct.Speed = GPIO_SPEED_FREQ_LOW;
HAL_GPIO_Init(GPIOF, &GPIO_InitStruct);
/*Configure GPIO pin : WK_UP_Pin */
GPIO_InitStruct.Pin = WK_UP_Pin;
GPIO_InitStruct.Mode = GPIO_MODE_IT_RISING;
GPIO_InitStruct.Pull = GPIO_PULLDOWN;
HAL_GPIO_Init(WK_UP_GPIO_Port, &GPIO_InitStruct);
/* EXTI interrupt init*/
HAL_NVIC_SetPriority(EXTI0_IRQn, 15, 0);
HAL_NVIC_EnableIRQ(EXTI0_IRQn);
HAL_NVIC_SetPriority(EXTI2_IRQn, 15, 0);
HAL_NVIC_EnableIRQ(EXTI2_IRQn);
HAL_NVIC_SetPriority(EXTI3_IRQn, 15, 0);
HAL_NVIC_EnableIRQ(EXTI3_IRQn);
HAL_NVIC_SetPriority(EXTI4_IRQn, 15, 0);
HAL_NVIC_EnableIRQ(EXTI4_IRQn);
}
cubeMX中CLOCK配置
RCC
Clock Configuration
引申
以上代码只是中断的示例代码,实际项目中需要消抖,判断短按,长按等。
推荐大家在实际项目中使用FreeRTOS系统为基础编写代码,退一步讲最起码也要实现消息队列以及系统节拍,比如msOS结构