STM32的USB例程修改步骤
一、usb_desc.c文件 根据你程序使用的通信方式修改。usb_desc.h文件中定义要根据usb_desc.c文件中的数组的大小;ConfigDescriptor[SIZ_CONFIG_DESC]下添加需要处理的端点;根据需要添加或删除报告描述符(主要用于HID)和CDC接口描述符(主要用于实现USB转串口)等。具体方法可以下载个“电脑圈圈”使用D12编写的例子。 二、Usb_conf.h文件: 1、修改需要处理那些中断 CNTR_CTRM 处理数据正确传输后控制,比如说响应主机 CNTR_DOVRM /* DMA OVeR/underrun Mask */ CNTR_ERRM /* ERRor Mask */ CNTR_WKUPM 0 /* WaKe UP Mask */ CNTR_SUSPM /* SUSPend Mask */ CNTR_RESETM 主要处理USB复位后进行一些初始化任务 CNTR_SOFM /* Start Of Frame Mask */ CNTR_ESOFM /* Expected Start Of Frame Mask */ 如: usb_conf.h中的#define IMR_MSK (CNTR_CTRM | CNTR_SOFM | CNTR_RESETM )是决定USB_CNTR寄存器中的那个USB相关中断启动还是屏蔽。 2、根据需要增加端点缓存地址,要根据缓存区的地址修改,防止数据重叠 如下为根据每个缓冲区的大小为64字节修改: #define ENDP1_TXADDR (0xC0) #define ENDP1_RXADDR (0xD0) #define ENDP2_TXADDR (0x100) #define ENDP2_RXADDR (0x140) #define ENDP3_TXADDR (0x180) #define ENDP3_RXADDR (0x1C0) 3、修改/* CTR service routines */下的EPX_IN_Callback和EPX_OUT_Callback。注释掉需要处理的函数。NOP_Process表示不处理。 三usb_prop.c文件 1、修改void XX_Reset(void)(如:void Joystick_Reset(void)) 一般/* Initialize Endpoint 0 */的不用修改,如下为举例说明端点1的初始化,其他端口原理一样。 SetEPType(ENDP1, EP_INTERRUPT);//设置端点1类型 /*EP_BULK 批量端点 EP_CONTROL 控制端点 EP_ISOCHRNOUS 同步端点 EP_INTERRUPT 中断端点*/ SetEPTxAddr(ENDP1, ENDP1_TXADDR); //设置端点1缓冲区基地址 SetEPTxCount(ENDP1, 64);// 配置Tx 缓冲计数器 SetEPRxStatus(ENDP1, EP_RX_DIS);// //设置端点接收关闭 SetEPTxStatus(ENDP1, EP_TX_NAK);// //设置端点1发送不应答 /* #define EP_RX_DIS (0x0000) // EndPoint RX DISabled 端点接收关闭 #define EP_RX_STALL (0x1000) // EndPoint RX STALLed 端点接收延迟 #define EP_RX_NAK (0x2000) // EndPoint RX NAKed 端点接收不应答 #define EP_RX_VALID (0x3000) // EndPoint RX VALID端点接收有效 #define EP_TX_DIS (0x0000) //EndPoint TX DISabled #define EP_TX_STALL (0x0010) // EndPoint TX STALLed #define EP_TX_NAK (0x0020) // EndPoint TX NAKed #define EP_TX_VALID (0x0030) // EndPoint TX VALID */ 2、删除不相干的描述符等。 如自定义的USB设备就不需要以下结构体初始化: ONE_DESCRIPTOR Joystick_Report_Descriptor ONE_DESCRIPTOR Mouse_Hid_Descriptor 3、修改RESULT XX_Data_Setup(u8 RequestNo)的数据类请求处理。 如Custom_HID例程修改为“自定义USB设备”例程时可以将以下代码删除 if ((RequestNo == GET_DESCRIPTOR) && (Type_Recipient == (STANDARD_REQUEST | INTERFACE_RECIPIENT)) && (pInformation->USBwIndex0 == 0)) { if (pInformation->USBwValue1 == REPORT_DESCRIPTOR) { CopyRoutine = Joystick_GetReportDescriptor; } else if (pInformation->USBwValue1 == HID_DESCRIPTOR_TYPE) { CopyRoutine = Joystick_GetHIDDescriptor; } } 4、删除不相干的获得描述符返回函数 如自定义的USB设备就不需要以下函数: Joystick_GetReportDescriptor Joystick_GetHIDDescriptor 四、usb_endp.c文件 1、增加之前定义的中断数据处理函数 如: void EP1_OUT_Callback(void) { 这些写接收代码 } 五、数据发送和接收,举例说明 1、数据接收 u8 DataLen; DataLen = GetEPRxCount(ENDP1); PMAToUserBufferCopy(TX1_buffer, ENDP1_RXADDR, DataLen); SetEPRxValid(ENDP1); USART1_Send(DataLen); count_out = 1; 2、数据发送 UserToPMABufferCopy(InBuffer, GetEPTxAddr(ENDP1), 64); SetEPTxCount(ENDP1, 64); SetEPTxValid(ENDP1); 如果你发送数据较为频繁,每次发送前应使用GetEPTxStatus(ENDP1)检测上次发送是否完成。如果端点状态处于EP_TX_VALID,说明发送未结束,如果端点状态处于EP_TX_NAK,说明发送结束。 |
|
来自: gastonfeng > 《USB》