STM32F4 DISC开发板vTaskNotifyGiveFromISR函数无法正常工作求助
问题描述
在STM32F4 DISC开发板上使用FreeRTOS V10.3.1内核时,调用ISR中的vTaskNotifyGiveFromISR函数无法触发预期的任务日志输出。
相关代码
任务创建(main.c)
TaskHandle_t handleRFInt; static TaskHandle_t initTask; xTaskCreate((TaskFunction_t) T_initTask, "start_task", 1024, NULL, 0, (TaskHandle_t *) initTask); xTaskCreate((TaskFunction_t) T_handleRFInt, "start_task", 1024, NULL, 0, (TaskHandle_t *) handleRFInt); vTaskStartScheduler();
初始化任务(T_initTask)
初始化PB9引脚及外部中断:
.... HAL_NVIC_SetPriority(EXTI9_5_IRQn, 5, 0); HAL_NVIC_EnableIRQ(EXTI9_5_IRQn); ....
中断回调函数
中断可正常触发(通过静态变量s_newRf95Interrupt能检测到),但任务通知无效:
void HAL_GPIO_EXTI_Callback(uint16_t GPIO_Pin) { BaseType_t xHigherPriorityTaskWoken = pdFALSE; if (GPIO_Pin == GPIO_PIN_9) { s_newRf95Interrupt = 1; vTaskNotifyGiveFromISR(handleRFInt ,&xHigherPriorityTaskWoken); portYIELD_FROM_ISR(xHigherPriorityTaskWoken); } }
中断处理任务(T_handleRFInt)
void T_handleRFInt(void const *argument) { static uint32_t thread_notification; while(1){ thread_notification = ulTaskNotifyTake(pdTRUE, portMAX_DELAY); if(thread_notification) { USER_LOG_INFO("here???"); } } }
问题诊断与修正
核心错误:任务句柄传递错误
xTaskCreate的最后一个参数要求传入任务句柄变量的地址,用于将创建成功后的任务句柄写入该变量。但你的代码中传递的是变量本身的强制转换,而非地址:
- 对于
initTask,你写了(TaskHandle_t *) initTask,正确写法是&initTask - 对于
handleRFInt,同样错误地传递了(TaskHandle_t *) handleRFInt,正确应为&handleRFInt
这导致handleRFInt始终是初始的无效空值,vTaskNotifyGiveFromISR实际上在操作一个无效句柄,自然无法通知到目标任务。
修正后的任务创建代码
TaskHandle_t handleRFInt; static TaskHandle_t initTask; // 修正:传递变量地址给xTaskCreate xTaskCreate((TaskFunction_t) T_initTask, "init_task", 1024, NULL, 0, &initTask); xTaskCreate((TaskFunction_t) T_handleRFInt, "rf_int_task", 1024, // 建议给任务设置唯一名称,便于调试 NULL, 0, &handleRFInt); vTaskStartScheduler();
额外检查项
- 中断优先级配置:FreeRTOS要求中断优先级必须低于
configMAX_SYSCALL_INTERRUPT_PRIORITY(定义在FreeRTOSConfig.h中),否则系统调用(如vTaskNotifyGiveFromISR)无法正常执行。需确认EXTI9_5_IRQn的优先级5是否符合该限制。 - 日志功能验证:在初始化任务中添加一条
USER_LOG_INFO输出,确认日志系统本身能正常工作,排除日志输出的问题。 - 任务优先级:当前两个任务优先级均为0,若系统存在更高优先级的任务,可能会抢占中断处理任务,但这不是当前问题的核心原因。
内容的提问来源于stack exchange,提问作者simon
相关产品推荐
相关产品推荐

