You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

STM32G0B1控制器未连接USB时FreeRTOS任务停止执行求助

STM32G0B1 USB断开后FreeRTOS任务阻塞问题排查

核心现象梳理

  • 基于STM32G0B1、CubeIDE/CubeMX配置,使用USB复合设备(CDC+HID)+ FreeRTOS,系统时钟64MHz(HSI+PLL),USB时钟用HSI48(时钟恢复暂关)
  • USB连主机时一切正常,断开后所有FreeRTOS任务阻塞,仅能在osDelay处暂停;重新连USB恢复正常
  • 不调用USBD_Start(&hUsbDeviceFS)时,任务完全正常
  • 断开后USB_CNTR的SUSPRDY、SUSPEN置位,无未触发的USB中断,TIM17时基IRQ状态正常,HardFault等中断未触发

可能原因及排查方向

1. USB挂起状态未正确处理

USB断开后自动进入挂起模式(SUSPEN置位),如果设备未配置自动唤醒或没有主动退出挂起的逻辑,可能导致USB外设占用总线资源,间接阻塞FreeRTOS调度:

  • 检查CubeMX的USB配置:是否开启了「USB Wakeup from suspend」?如果没开,设备进入挂起后无法主动退出,会一直占用相关硬件资源。
  • 手动清除挂起标志:在空闲任务或低优先级任务中定期检查USB状态,当检测到设备断开(可通过USBD状态机或硬件连接引脚判断),执行以下代码强制退出挂起:
if ((USB_CNTR & (USB_CNTR_SUSPEN | USB_CNTR_SUSPRDY)) != 0)
{
  USB_CNTR &= ~(USB_CNTR_SUSPEN | USB_CNTR_SUSPRDY);
  __HAL_PCD_UNGATE_PHYCLOCK(&hpcd_USB_FS); // 重新开启USB PHY时钟
}

2. USB相关任务阻塞导致调度器异常

如果有高优先级的USB任务(比如CDC数据收发)在等待主机响应,断开后该任务会一直处于阻塞状态,抢占了调度器资源:

  • 用CubeIDE的FreeRTOS任务查看器:断开USB后观察各任务的状态(运行/阻塞/挂起),确认是否有高优先级任务一直占用CPU或异常阻塞。
  • 调整USB任务优先级:降低CDC/HID相关任务的优先级,确保SysTick中断(FreeRTOS调度核心)能正常触发调度。

3. 中断优先级配置冲突

USB中断优先级如果高于FreeRTOS的SysTick中断,可能在挂起时干扰调度器的正常切换:

  • 检查中断优先级:确保USB_UCPD1_2_IRQn的优先级低于SysTick_IRQn(默认SysTick是最低优先级)。
  • 验证中断服务函数:确认USB_UCPD1_2_IRQHandler中正确调用了HAL_PCD_IRQHandler(&hpcd_USB_FS),没有遗漏或错误的处理逻辑导致中断异常挂起。

4. HSI48时钟异常牵连系统总线

虽然系统时钟用的是HSI+PLL,但HSI48和系统总线可能存在共享的时钟树节点,USB挂起时HSI48的异常状态可能影响系统总线:

  • 开启HSI48时钟恢复功能:当前关闭了该功能,开启后测试是否能避免时钟异常导致的阻塞。
  • 检查时钟树配置:确认HSI48仅独立供给USB外设,未与系统时钟总线共享关键节点。

内容的提问来源于stack exchange,提问作者Tilo

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.08 07:08:35