单片机学习小组
登录
直播中
早知
9年用户
1294经验值
擅长:光电显示 存储技术
私信
关注
请问STM32F107VC运行STM32CubeMX生成的USB_OTG Mass Storage工程无法识别USB设备怎么解决?
开启该帖子的消息推送
请问
STM32
F107VC运行STM32CubeMX生成的USB_OTG Mass Storage工程无法识别USB设备怎么解决?
回帖
(1)
曹昆
2022-2-22 09:29:59
这是因为:CubeMX生成的代码里面,没有响应OTG_FS_IRQn中断。
USB设备模式的电路如下。该电路适合所有的STM32型号。
红框部分为上拉电阻,STM32F1(如STM32F103和STM32F107)才需要这部分电路,而STM32F4就可以不要。这是因为STM32F4的USB_OTG_GCCFG寄存器里面有NOVBUSSENS这一位,可以打开内部的上拉电阻,而STM32F1却没有。
当PE1(可以选择其他I/O口)为低电平时使能上拉电阻,主机认为USB设备已插入。当PE1为高电平时,主机认为USB设备已拔出。正常情况下应该使PE1输出低电平。
STM32F107VC的时钟配置如下。保证USB有48MHz的时钟。
USB配置为Device Only模式,只需要两个引脚(PA11和PA12)就可以实现USB设备。
确保PE1配置为输出低电平。
生成工程后,打开stm32f1xx_it.c,可以发现里面根本没有USB OTG的中断处理函数,尽管CubeMX里面勾选了USB OTG中断处理(灰色必选),然而这并不能改变USB OTG中断处理函数没有生成的事实。
于是添加如下代码:
extern PCD_HandleTypeDef hpcd_USB_OTG_FS;
void OTG_FS_IRQHandler(void)
{
HAL_PCD_IRQHandler(&hpcd_USB_OTG_FS);
}
还要打开u***d_conf.c,找到HAL_PCD_MspInit函数,在里面打开USB OTG的中断。
(连打开USB中断的代码都没有。。。)
/* USER CODE BEGIN USB_OTG_FS_MspInit 1 */
HAL_NVIC_EnableIRQ(OTG_FS_IRQn);
/* USER CODE END USB_OTG_FS_MspInit 1 */
烧写后,再运行程序,问题就解决了。可以在电脑里面看到U盘盘符了。
另外,如果发现USB设备能够成功枚举但无法启动,则可能是malloc分配内存失败导致的。
打开u***d_conf.h,检查USBD_malloc和USBD_free的定义。如果是下面的定义,是不会出问题的。
/* Memory management macros */
/** Alias for memory allocation. */
#define USBD_malloc (uint32_t *)USBD_static_malloc
/** Alias for memory release. */
#define USBD_free USBD_static_free
如果定义的是malloc和free,那就很可能内存分配失败,USBD_malloc返回了NULL导致USB 端点1没有开启。
/* Memory management macros */
#define USBD_malloc malloc
#define USBD_free free
在Mass Storage的USBD_MSC_Init函数里面会调用USBD_malloc函数分配8300字节的内存用于存储USBD_MSC_BOT_HandleTypeDef结构体的内容。这远远超出了启动文件(如startup_stm32f103xb.s)里面定义的堆内存的大小Heap_Size。
pdev->pClassData = USBD_malloc(sizeof(USBD_MSC_BOT_HandleTypeDef));
Heap_Size默认为0x200,加上8300(=0x206c)后是0x226c,可以把Heap_Size定义为0x2400。
——————————————————————————————————————————————————————
这里顺便说一下,STM32F103里面的从USB,收发数据靠的是读写512字节的PMA(Packet Memory Area),其地址为0x40006000~0x400063fd。第0个字节是0x40006000,第1个字节是0x40006001;第2个字节是0x40006004,第3个字节是0x40006005;第4个字节是0x40006008,第5个字节是0x40006009……以此类推,直到第511个字节0x400063fd。
而STM32F107里面的USB OTG,收发数据靠的是1.25KB的DFIFO。定义:
#define USB_OTG_FS_PERIPH_BASE 0x50000000UL
#define USB_OTG_FIFO_BASE 0x00001000UL
#define USB_OTG_FS_DFIFO ((USB_OTG_DFIFOTypeDef *)(USB_OTG_FS_PERIPH_BASE + USB_OTG_FIFO_BASE))
typedef struct
{
uint32_t DFIFO;
uint32_t RESERVED[1023];
} USB_OTG_DFIFOTypeDef;
则接收数据始终是读取USB_OTG_FS_DFIFO->DFIFO寄存器(相当于USB_OTG_FS_DFIFO[0].DFIFO),而发送数据是写USB_OTG_FS_DFIFO[端点号].DFIFO寄存器。
——————————————————————————————————————————————————————
2021年3月6日补充:今天突然发现u***d_storage_if.c里面STORAGE_BLK_SIZ由512改成4096后,插上电脑U盘盘符就出不来了。
仔细检查后发现,CubeMX里面MSC_MEDIA_PACKET也要改成4096才行。
还有就是要注意,如果读写SPI Flash存储器(如W25Q128)用了DMA,就要保证USB中断的优先级
低于
DMA中断的优先级,否则读数据时将卡在USB中断里面出不来。
这是因为:CubeMX生成的代码里面,没有响应OTG_FS_IRQn中断。
USB设备模式的电路如下。该电路适合所有的STM32型号。
红框部分为上拉电阻,STM32F1(如STM32F103和STM32F107)才需要这部分电路,而STM32F4就可以不要。这是因为STM32F4的USB_OTG_GCCFG寄存器里面有NOVBUSSENS这一位,可以打开内部的上拉电阻,而STM32F1却没有。
当PE1(可以选择其他I/O口)为低电平时使能上拉电阻,主机认为USB设备已插入。当PE1为高电平时,主机认为USB设备已拔出。正常情况下应该使PE1输出低电平。
STM32F107VC的时钟配置如下。保证USB有48MHz的时钟。
USB配置为Device Only模式,只需要两个引脚(PA11和PA12)就可以实现USB设备。
确保PE1配置为输出低电平。
生成工程后,打开stm32f1xx_it.c,可以发现里面根本没有USB OTG的中断处理函数,尽管CubeMX里面勾选了USB OTG中断处理(灰色必选),然而这并不能改变USB OTG中断处理函数没有生成的事实。
于是添加如下代码:
extern PCD_HandleTypeDef hpcd_USB_OTG_FS;
void OTG_FS_IRQHandler(void)
{
HAL_PCD_IRQHandler(&hpcd_USB_OTG_FS);
}
还要打开u***d_conf.c,找到HAL_PCD_MspInit函数,在里面打开USB OTG的中断。
(连打开USB中断的代码都没有。。。)
/* USER CODE BEGIN USB_OTG_FS_MspInit 1 */
HAL_NVIC_EnableIRQ(OTG_FS_IRQn);
/* USER CODE END USB_OTG_FS_MspInit 1 */
烧写后,再运行程序,问题就解决了。可以在电脑里面看到U盘盘符了。
另外,如果发现USB设备能够成功枚举但无法启动,则可能是malloc分配内存失败导致的。
打开u***d_conf.h,检查USBD_malloc和USBD_free的定义。如果是下面的定义,是不会出问题的。
/* Memory management macros */
/** Alias for memory allocation. */
#define USBD_malloc (uint32_t *)USBD_static_malloc
/** Alias for memory release. */
#define USBD_free USBD_static_free
如果定义的是malloc和free,那就很可能内存分配失败,USBD_malloc返回了NULL导致USB 端点1没有开启。
/* Memory management macros */
#define USBD_malloc malloc
#define USBD_free free
在Mass Storage的USBD_MSC_Init函数里面会调用USBD_malloc函数分配8300字节的内存用于存储USBD_MSC_BOT_HandleTypeDef结构体的内容。这远远超出了启动文件(如startup_stm32f103xb.s)里面定义的堆内存的大小Heap_Size。
pdev->pClassData = USBD_malloc(sizeof(USBD_MSC_BOT_HandleTypeDef));
Heap_Size默认为0x200,加上8300(=0x206c)后是0x226c,可以把Heap_Size定义为0x2400。
——————————————————————————————————————————————————————
这里顺便说一下,STM32F103里面的从USB,收发数据靠的是读写512字节的PMA(Packet Memory Area),其地址为0x40006000~0x400063fd。第0个字节是0x40006000,第1个字节是0x40006001;第2个字节是0x40006004,第3个字节是0x40006005;第4个字节是0x40006008,第5个字节是0x40006009……以此类推,直到第511个字节0x400063fd。
而STM32F107里面的USB OTG,收发数据靠的是1.25KB的DFIFO。定义:
#define USB_OTG_FS_PERIPH_BASE 0x50000000UL
#define USB_OTG_FIFO_BASE 0x00001000UL
#define USB_OTG_FS_DFIFO ((USB_OTG_DFIFOTypeDef *)(USB_OTG_FS_PERIPH_BASE + USB_OTG_FIFO_BASE))
typedef struct
{
uint32_t DFIFO;
uint32_t RESERVED[1023];
} USB_OTG_DFIFOTypeDef;
则接收数据始终是读取USB_OTG_FS_DFIFO->DFIFO寄存器(相当于USB_OTG_FS_DFIFO[0].DFIFO),而发送数据是写USB_OTG_FS_DFIFO[端点号].DFIFO寄存器。
——————————————————————————————————————————————————————
2021年3月6日补充:今天突然发现u***d_storage_if.c里面STORAGE_BLK_SIZ由512改成4096后,插上电脑U盘盘符就出不来了。
仔细检查后发现,CubeMX里面MSC_MEDIA_PACKET也要改成4096才行。
还有就是要注意,如果读写SPI Flash存储器(如W25Q128)用了DMA,就要保证USB中断的优先级
低于
DMA中断的优先级,否则读数据时将卡在USB中断里面出不来。
举报
更多回帖
rotate(-90deg);
回复
相关问答
如何使用
STM32CubeMX
快速
生成
USB
HID
工程
呢
2021-10-27
1725
请问
STM32F
303RE是否支持
USB_OTG
连接?
2023-01-04
269
PC主机
无法
检测到
STM32F
769I
USB
OTG
设备
外设咋办
2022-12-20
374
STM32F107
VCT6
运行
《virtual com port》系统显示“
无法
识别
的u***
设备
2014-06-05
9135
STM32CubeMX
生成
的
工程
在keil中不能
识别
CooCox仿真器JTAG
2019-05-05
5073
stm32cubemx
生成
工程
后
USB
转串口出现黄色感叹号怎么解决?
2022-02-21
8201
在平台设置选项卡上的
USB
_HOST中设置STM3
CubeMX
期间出现警告如何解决?
2023-01-05
240
怎么基于
STM32
实现U盘访问?
2019-08-08
8903
STM32CubeMX
软件
生成
工程
怎么实现?
2020-11-05
1970
为什么
STM32CubeMX
带FreeRTOS
生成
Keil
工程
的程序
无法
下载
运行
呢
2021-11-26
1671
发帖
登录/注册
20万+
工程师都在用,
免费
PCB检查工具
无需安装、支持浏览器和手机在线查看、实时共享
查看
点击登录
登录更多精彩功能!
首页
论坛版块
小组
免费开发板试用
ebook
直播
搜索
登录
×
20
完善资料,
赚取积分