STM32 USB学习笔记
一、USB-FS-Device firmware library
使用固件库开发程序,需要包含几个文件
从图中可见,应用程序接口部分,有:usb_pwr, usb_conf, usb_desc, usb_istr, usb_prop, usb_endp六个文件,在设备驱动中有六个文件:usb_core, usb_init, usb_sil, usb_int, usb_regs, usb_mem。
usb_regs:它提供了访问USB设备外围接口寄存器的基本过程。
usb_int:处理正确传输服务程序,提供了USB协议事件和库的联系
usb_mem:提供用户存储区和包存储区的数据交换。
usb_init :设置在库中要使用的初始化程序和全局变量
usb_core: 实现在USB2.0协议第9章中的所有功能。
usb_sil :实现外围接口的抽象层,它提供的过程实现端点的读写。
---------
usb_conf.h:Define the BTABLE and all endpoint addresses in the PMA.
Define the interrupt mask according to the needed events.
usb_desc :包括所有应用层的描述符。
usb_prop :为USB核提供的Device_Property、Device_Table、 USER_STANDARD_REQUEST 结构
usb_endp:
usb_istr:
usb_pwr:
实例调试
USB_Init(),里面只调用了一个函数,pProperty->Init();这个函数是什么呢?当右击这个函数出现的快捷菜单中,选择 Go to defined of Init 时,无法找到这个函数。这是怎么回事呢?实际上,向前面看,有一个pProperty = &Device_Property,噢,原来把这个指针指向了Device_Property,那么,再找一下它的定义,有一个结构:
DEVICE_PROP Device_Property =
{
MASS_init,
MASS_Reset,
MASS_Status_In,
MASS_Status_Out,
MASS_Data_Setup,
MASS_NoData_Setup,
MASS_Get_Interface_Setting,
MASS_GetDeviceDescriptor,
MASS_GetConfigDescriptor,
MASS_GetStringDescriptor,
0,
0x40 /*MAX PACKET SIZE*/
};
可见,这个Init实际上就是MASS_init函数了,这个函数里有几个调用,一个是Get_SerialNum函数,里面有这个
Device_Serial0 = *(__IO uint32_t*)(0x1FFFF7E8);
Device_Serial1 = *(__IO uint32_t*)(0x1FFFF7EC);
Device_Serial2 = *(__IO uint32_t*)(0x1FFFF7F0);
这里用了绝对地址调,指向0x1FFFF7E8以后的几个字节的内容,它放的是什么呢?手册中说了:Unique device ID register (96 bits)
下一个是PowerOn函数,它是设置CNTR、ISTR寄存器的,首先强制USB复位,再设置中断。
还有一个调用:USB_SIL_Init,它又重新设置了CNTR寄存器的内容。
好了,初始化部分结束了。USB在处理时,输入和输出都采用中断形式,可以使用的中断有两个0x8C和0x90,它是和CAN共用的。在0x8C处调用的是CTR_HP函数,在0x90处调用的是USB_Istr函数。
USB_Istr函数是根据CNTR的设置,以及读取ISTR的状态来决定要执行的过程,还有根据对Callback的定义,来执行相应的Callback。其中CTR_LP是一个主要过程。它主要根据传输方向及端点种类决定执行的三个过程,In0_Process,Setup0_Process,Out0_Process。
对于CTR_HP函数,判断中断状态,来执行EP2_OUT_Callback(又调用了过程 Mass_Storage_Out)或EP1_IN_Callback(它又调用了Mass_Storage_In),
CAN和USB共用中断问题,可根据中断寄存器状态判断处理,由于对这些位的读出不影响其内容,因此不用保存。
if (wInterrupt_Mask & _GetISTR())
USB_Istr();
else if ((CAN1->RF0R) & 0x1B)
{
……
}
修改MAL_Init、MAL_GetStatus、MAL_Write、MAL_Read
与具体存储介质打交道的就是这三个函数,MAL_Init对介质进行初始化,MAL_GetStatus提供介质信息,对于SPI Flash,要解除写保护,才能实现格式化等写入工作,