1、概論:git
在STM32_USB-FS-Device_Lib_V4.1.0的Custom_HID工程基礎上進行修改;ide
開發一款設備,有三個HID接口,mouse+pen+自定義HID函數
其中:0_HID 是mouse(端點1 IN);1_HID 是pen(端點2 IN);2_HID 是自定義(端點3 IN-OUT)。測試
在設備管理器和bus hound能夠看到以下:ui
2、修改步驟:this
一、修改設備$$配置描述符spa
/* USB Standard Device Descriptor */ const uint8_t CustomHID_DeviceDescriptor[CUSTOMHID_SIZ_DEVICE_DESC] = { 0x12, /*bLength */ USB_DEVICE_DESCRIPTOR_TYPE, /*bDescriptorType*/ 0x10, /*bcdUSB */ 0x01, 0x00, /*bDeviceClass*/ 0x00, /*bDeviceSubClass*/ 0x00, /*bDeviceProtocol*/ 0x40, /*bMaxPacketSize:64 bytes*/ LOBYTE(USBD_VID), /*idVendor*/ HIBYTE(USBD_VID), /*idVendor*/ LOBYTE(USBD_PID), /*idVendor*/ HIBYTE(USBD_PID), /*idVendor*/ 0x00, /*bcdDevice rel. 00.00*/ 0x00, USBD_IDX_MFC_STR, /*Index of manufacturer string*/ USBD_IDX_PRODUCT_STR, /*Index of product string*/ USBD_IDX_SERIAL_STR, /*Index of serial number string*/ USBD_CFG_MAX_NUM /*bNumConfigurations*/ }; /* CustomHID_DeviceDescriptor */ /* USB Configuration Descriptor */ /* All Descriptors (Configuration, Interface, Endpoint, Class, Vendor */ const uint8_t CustomHID_ConfigDescriptor[CUSTOMHID_SIZ_CONFIG_DESC] = { /************** Configuration Descriptor Bus Powered, 100 mA ****************/ 0x09, /* bLength: Configuration Descriptor size */ USB_CONFIGURATION_DESCRIPTOR_TYPE, /* bDescriptorType: Configuration */ 0x5b, /* wTotalLength: Bytes returned */ 0x00, 0x03, /* bNumInterfaces: 1 interface *///3個HID接口 0x01, /* bConfigurationValue: Configuration value */ 0x00, /* iConfiguration: Index of string descriptor describing the configuration*/ 0xA0, /* bmAttributes: Self powered:C0 Bus Powered, Remote Wakeup:A0 */ 0x32, /* MaxPower 100 mA: this current is used for detecting Vbus */ // 0/0 HID 1 Endpoint IN of 端點1 /************** Descriptor of 0/0 HID interface ****************/ /* 09 */ 0x09, /* bLength: Interface Descriptor size */ USB_INTERFACE_DESCRIPTOR_TYPE,/* bDescriptorType: Interface descriptor type */ 0x00, /* bInterfaceNumber: Number of Interface */ 0x00, /* bAlternateSetting: Alternate setting */ 0x01, /* bNumEndpoints */ 0x03, /* bInterfaceClass: HID */ 0x01, /* bInterfaceSubClass : 1=BOOT, 0=no boot */ 0x02, /* nInterfaceProtocol : 0=none, 1=keyboard, 2=mouse */ 0x00, /* iInterface: Index of string descriptor */ /******************** Descriptor of 0/0 HID ********************/ /* 18 */ 0x09, /* bLength: HID Descriptor size */ HID_DESCRIPTOR_TYPE, /* bDescriptorType: HID */ 0x00, /*bcdHID: HID Class Spec release number*/ 0x01, 0x00, /* bCountryCode: Hardware target country */ 0x01, /* bNumDescriptors: Number of HID class descriptors to follow */ 0x22, /* bDescriptorType */ sizeof(mouse_ReportDescriptor)&0xFF, /* wItemLength: Total length of Report descriptor :177 bytes*/ (sizeof(mouse_ReportDescriptor)>>8)&0xFF, /******************** Descriptor of 0/0 HID endpoints :1IN ******************/ /* 27 */ 0x07, /* bLength: Endpoint Descriptor size */ USB_ENDPOINT_DESCRIPTOR_TYPE, /* bDescriptorType: */ 0x81, /* bEndpointAddress: Endpoint Address (IN) */ 0x03, /* bmAttributes: Interrupt endpoint */ 0x08, /* wMaxPacketSize: 8 Bytes max */ 0x00, 0x04, /* bInterval: Polling Interval (4 ms) */ // 1/0 HID 1 Endpoint IN of 端點2 /************** Descriptor of 1/0 HID interface ****************/ /* 34 */ 0x09, /* bLength: Interface Descriptor size */ USB_INTERFACE_DESCRIPTOR_TYPE,/* bDescriptorType: Interface descriptor type */ 0x01, /* bInterfaceNumber: Number of Interface */ 0x00, /* bAlternateSetting: Alternate setting */ 0x01, /* bNumEndpoints */ 0x03, /* bInterfaceClass: HID */ 0x01, /* bInterfaceSubClass : 1=BOOT, 0=no boot */ 0x02, /* nInterfaceProtocol : 0=none, 1=keyboard, 2=mouse */ 0x00, /* iInterface: Index of string descriptor */ /******************** Descriptor of 1/0 HID ********************/ /* 43 */ 0x09, /* bLength: HID Descriptor size */ HID_DESCRIPTOR_TYPE, /* bDescriptorType: HID */ 0x00, /*bcdHID: HID Class Spec release number*/ 0x01, 0x00, /* bCountryCode: Hardware target country */ 0x01, /* bNumDescriptors: Number of HID class descriptors to follow */ 0x22, /* bDescriptorType */ sizeof(pen_ReportDescriptor)&0xFF, /* wItemLength: Total length of Report descriptor :237 bytes*/ (sizeof(pen_ReportDescriptor)>>8)&0xFF, /******************** Descriptor of 1/0 HID endpoints :2 IN ******************/ /* 52 */ 0x07, /* bLength: Endpoint Descriptor size */ USB_ENDPOINT_DESCRIPTOR_TYPE, /* bDescriptorType: */ 0x82, /* bEndpointAddress: Endpoint Address (IN) */ 0x03, /* bmAttributes: Interrupt endpoint */ 0x40, /* wMaxPacketSize: 64 Bytes max */ 0x00, 0x03, /* bInterval: Polling Interval (3 ms) */ // 2/0 HID 1 Endpoint IN /1 Endpoint OUT of 端點3 /************** Descriptor of 2/0 HID interface ****************/ /* 59 */ 0x09, /* bLength: Interface Descriptor size */ USB_INTERFACE_DESCRIPTOR_TYPE,/* bDescriptorType: Interface descriptor type */ 0x02, /* bInterfaceNumber: Number of Interface */ 0x00, /* bAlternateSetting: Alternate setting */ 0x02, /* bNumEndpoints */ 0x03, /* bInterfaceClass: HID */ 0x00, /* bInterfaceSubClass : 1=BOOT, 0=no boot */ 0x00, /* nInterfaceProtocol : 0=none, 1=keyboard, 2=mouse */ 0x00, /* iInterface: Index of string descriptor */ /******************** Descriptor of 2/0 HID ********************/ /* 68 */ 0x09, /* bLength: HID Descriptor size */ HID_DESCRIPTOR_TYPE, /* bDescriptorType: HID */ 0x00, /*bcdHID: HID Class Spec release number*/ 0x01, 0x00, /* bCountryCode: Hardware target country */ 0x01, /* bNumDescriptors: Number of HID class descriptors to follow */ 0x22, /* bDescriptorType */ sizeof(HID_driver_ReportDescriptor)&0xFF, /* wItemLength: Total length of Report descriptor :36 bytes*/ (sizeof(HID_driver_ReportDescriptor)>>8)&0xFF, /******************** Descriptor of 2/0 HID endpoints :3 In, Interrupt, 3 ms******************/ /* 77 */ 0x07, /* bLength: Endpoint Descriptor size */ USB_ENDPOINT_DESCRIPTOR_TYPE, /* bDescriptorType: */ 0x83, /* bEndpointAddress: Endpoint Address (IN) */ 0x03, /* bmAttributes: Interrupt endpoint */ 0x0A, /* wMaxPacketSize: 10 Bytes max */ 0x00, 0x03, /* bInterval: Polling Interval (3 ms) */ /******************** Descriptor of 2/0 HID endpoints :3 Out, Interrupt, 3 ms******************/ /* 84 */ 0x07, /* bLength: Endpoint Descriptor size */ USB_ENDPOINT_DESCRIPTOR_TYPE, /* bDescriptorType: */ 0x03, /* bEndpointAddress: Endpoint Address (out) */ 0x03, /* bmAttributes: Interrupt endpoint */ 0x0A, /* wMaxPacketSize: 10 Bytes max */ 0x00, 0x0A, /* bInterval: Polling Interval (10 ms) */ }; /* CustomHID_ConfigDescriptor */
二、分別修改報告描述符.net
1 /* 如下分別是三個報告描述符 */ 2 /*Interface 0 HID Report Descriptor Mouse*/ 3 const uint8_t mouse_ReportDescriptor[mouse_SIZ_REPORT_DESC] = 4 { 5 /*******************************mouse 1******************************************/ 6 0x05, 0x01,/*USAGE_PAGE (Generic Desktop)*/ 7 0x09, 0x02,/*USAGE (Mouse)*/ 8 0xA1, 0x01,/*COLLECTION (Application)*/ 9 10 0x85, 0x09,//Report ID (9) 11 0x09, 0x01,//Usage (Pointer) 12 0xA1, 0x00,//Collection (Physical) 13 14 0x05, 0x09,//Usage Page (Button) 15 0x19, 0x01,//USAGE_MINIMUM(1) 16 0x29, 0x03,//USAGE_MAXIMUM(3) 17 0x15, 0x00,//LOGICAL_MINIMUM (0) 18 0x25, 0x01,//LOGICAL_MAXIMUM (1) 19 0x75, 0x01,//REPORT_SIZE (1) 20 0x95, 0x03,//Report Count (3) 21 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 22 23 0x95, 0x05,//Report Count (5) 24 0x81, 0x01,//Input (Cnst,Ary,Abs) 25 26 0x05, 0x01,//Usage Page (Generic Desktop) 27 0x09, 0x30,//Usage (X) 28 0x09, 0x31,//Usage (Y) 29 0x26, 0xFF,0x7F,//Logical Maximum (32767) 30 0x95, 0x02,//Report Count (2) 31 0x75, 0x10,//Report Size (16) 32 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 33 34 0x05, 0x0D,//Usage Page (Digitizer) 35 0x09, 0x30,//Usage (Tip Pressure) 36 0x26, 0xFF,0x07,//Logical Maximum (2047) 37 0x95, 0x01,//Report Count (1) 38 0x75, 0x10,//Report Size (16) 39 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 40 41 0xC0,//End Collection 42 0xC0,//End Collection 43 44 /*******************************mouse 2-75******************************************/ 45 0x05, 0x01,/*USAGE_PAGE (Generic Desktop)*/ 46 0x09, 0x02,/*USAGE (Mouse)*/ 47 0xA1, 0x01,/*COLLECTION (Application)*/ 48 49 0x85, 0x01,//Report ID (1) 50 0x09, 0x01,//Usage (Pointer) 51 0xA1, 0x00,//Collection (Physical) 52 53 0x05, 0x09,//Usage Page (Button) 54 0x19, 0x01,//USAGE_MINIMUM(1) 55 0x29, 0x05,//USAGE_MAXIMUM(5) 56 0x15, 0x00,//LOGICAL_MINIMUM (0) 57 0x25, 0x01,//LOGICAL_MAXIMUM (1) 58 0x75, 0x01,//REPORT_SIZE (1) 59 0x95, 0x05,//Report Count (5) 60 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 61 62 0x95, 0x03,//Report Count (3) 63 0x81, 0x01,//Input (Cnst,Ary,Abs) 64 65 0x05, 0x01,//Usage Page (Generic Desktop) 66 0x09, 0x30,//Usage (X) 67 0x09, 0x31,//Usage (Y) 68 0x95, 0x02,//Report Count (2) 69 0x75, 0x10,//Report Size (16) 70 0x16, 0x00,0x80,//Logical Minimum (-32767) 71 0x26, 0xFF,0x7F,//Logical Maximum (32767) 72 0x81, 0x06,//Input (Data,Var,Rel,NWrp,Lin,Pref,NNul,Bit) 73 74 0x09, 0x38,//Usage (Wheel) 75 0x15, 0x81,//Logical Minimum (-127) 76 0x25, 0x7F,//Logical Maximum (127) 77 0x95, 0x01,//Report Count (1) 78 0x75, 0x08,//Report Size (8) 79 0x81, 0x06,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 80 81 0x05, 0x0C,//Usage Page (Consumer Devices) 82 0x0A, 0x38,0x02,//Usage (AC Pan)47) 83 0x95, 0x01,//Report Count (1) 84 0x75, 0x08,//Report Size (8) 85 0x81, 0x06,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 86 87 0xC0,//End Collection 88 0xC0,//End Collection 89 90 /********************************Keyboard-40*******************************************/ 91 0x05, 0x01,/*USAGE_PAGE (Generic Desktop)*/ 92 0x09, 0x06,/*USAGE (Keyboard)*/ 93 0xA1, 0x01,/*COLLECTION (Application)*/ 94 95 0x85, 0x06,//Report ID (6)--------------------------無驅動按鍵使用此report 96 0x05, 0x07,//Usage Page (Keyboard/Keypad) 97 0x19, 0xE0,//USAGE_MINIMUM(Keyboard Left Control) 98 0x29, 0xE7,//USAGE_MAXIMUM(Keyboard Right GUI) 99 0x15, 0x00,//LOGICAL_MINIMUM (0) 100 0x25, 0x01,//LOGICAL_MAXIMUM (1) 101 0x75, 0x01,//REPORT_SIZE (1) 102 0x95, 0x08,//Report Count (8) 103 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 104 105 0x05, 0x07,//Usage Page (Keyboard/Keypad) 106 0x19, 0x00,//Usage Minimum (Undefined) 107 0x29, 0xFF,//Usage Maximum 108 0x26, 0xFF,0x00,//Logical Maximum (255) 109 0x95, 0x06,//Report Count (6) 110 0x75, 0x10,//Report Size (8) 111 0x81, 0x00,//Input (Data,Ary,Abs) 112 113 0xC0//End Collection 114 }; 115 116 /*Interface 1 HID Report Descriptor Pen*/ 117 const uint8_t pen_ReportDescriptor[pen_SIZ_REPORT_DESC] = 118 { 119 /*******************************pen 1****x2**************************************/ 120 0x05, 0x0D,/*Usage Page (Digitizer)*/ 121 0x09, 0x02,/*Usage (Pen)*/ 122 0xA1, 0x01,/*COLLECTION (Application)*/ 123 124 0x85, 0x07,//Report ID (7) 125 0x09, 0x20,//Usage (Stylus) 126 0xA1, 0x00,//Collection (Physical) 127 128 0x09, 0x42,//Usage (Tip Switch) 129 0x09, 0x44,//Usage (Barrel Switch) 130 0x09, 0x45,//Usage (Eraser) 131 0x15, 0x00,//LOGICAL_MINIMUM (0) 132 0x25, 0x01,//LOGICAL_MAXIMUM (1) 133 0x75, 0x01,//REPORT_SIZE (1) 134 0x95, 0x03,//Report Count (3) 135 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 136 137 0x95, 0x02,//Report Count (2) 138 0x81, 0x03,//Input (Cnst,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 139 140 0x09, 0x32,//Usage (In Range) 141 0x95, 0x01,//Report Count (1) 142 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 143 144 0x95, 0x02,//Report Count (2) 145 0x81, 0x03,//Input (Cnst,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 146 147 0x95, 0x01,//Report Count (1) 148 0x75, 0x10,//Report Size (16) 149 0x35, 0x00,//Physical Minimum (0) 150 151 0xA4,//Push 152 0x05, 0x01,//Usage Page (Generic Desktop) 153 0x09, 0x30,//Usage (X) 154 0x65, 0x13,//Unit (Eng Lin: Length (in)) 155 0x55, 0x0D,//Unit Exponent (-3) 156 0x46, 0xC1,0x28,//Physical Maximum (10433) 157 0x46, 0xC2,0x65,//Logical Maximum (26050) 158 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 159 0x09, 0x31,//Usage (Y) 160 0x46, 0x9B,0x18,//Physical Maximum (6299) 161 0x26, 0x80,0x3E,//Logical Maximum (16000) 162 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 163 0xB4,//Pop 164 165 0x09, 0x30,//Usage (Tip Pressure) 166 0x45, 0x00,//Physical Maximum (0) 167 0x26, 0xFF,0x1F,//Logical Maximum (8191) 168 0x81, 0x42,//Input (Data,Var,Abs,NWrp,Lin,Pref,Null,Bit) 169 0x09, 0x3D,//Usage (X Tilt) 170 0x15, 0x81,//Logical Minimum (-127) 171 0x25, 0x7F,//Logical Maximum (127) 172 0x95, 0x01,//Report Count (1) 173 0x75, 0x08,//Report Size (8) 174 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 175 176 0x09, 0x3E,//Usage (Y Tilt) 177 0x15, 0x81,//Logical Minimum (-127) 178 0x25, 0x7F,//Logical Maximum (127) 179 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 180 0xC0,//End Collection 181 0xC0,//End Collection 182 183 /*******************************pen 2******************************************/ 184 0x05, 0x0D,/*Usage Page (Digitizer)*/ 185 0x09, 0x02,/*Usage (Pen)*/ 186 0xA1, 0x01,/*COLLECTION (Application)*/ 187 188 0x85, 0x08,//Report ID (8) 189 0x09, 0x20,//Usage (Stylus) 190 0xA1, 0x00,//Collection (Physical) 191 192 0x09, 0x42,//Usage (Tip Switch) 193 0x09, 0x44,//Usage (Barrel Switch) 194 0x09, 0x45,//Usage (Eraser) 195 0x15, 0x00,//LOGICAL_MINIMUM (0) 196 0x25, 0x01,//LOGICAL_MAXIMUM (1) 197 0x75, 0x01,//REPORT_SIZE (1) 198 0x95, 0x03,//Report Count (3) 199 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 200 201 0x95, 0x02,//Report Count (2) 202 0x81, 0x03,//Input (Cnst,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 203 204 0x09, 0x32,//Usage (In Range) 205 0x95, 0x01,//Report Count (1) 206 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 207 208 0x95, 0x02,//Report Count (2) 209 0x81, 0x03,//Input (Cnst,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 210 211 0x95, 0x01,//Report Count (1) 212 0x75, 0x10,//Report Size (16) 213 0x35, 0x00,//Physical Minimum (0) 214 215 0xA4,//Push 216 0x05, 0x01,//Usage Page (Generic Desktop) 217 0x09, 0x30,//Usage (X) 218 0x65, 0x13,//Unit (Eng Lin: Length (in)) 219 0x55, 0x0D,//Unit Exponent (-3) 220 0x46, 0xC1,0x28,//Physical Maximum (10433) 221 0x46, 0xC2,0x65,//Logical Maximum (26050) 222 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 223 0x09, 0x31,//Usage (Y) 224 0x46, 0x9B,0x18,//Physical Maximum (6299) 225 0x26, 0x80,0x3E,//Logical Maximum (16000) 226 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 227 0xB4,//Pop 228 229 0x09, 0x30,//Usage (Tip Pressure) 230 0x45, 0x00,//Physical Maximum (0) 231 0x26, 0xFF,0x1F,//Logical Maximum (8191) 232 0x81, 0x42,//Input (Data,Var,Abs,NWrp,Lin,Pref,Null,Bit) 233 0x09, 0x3D,//Usage (X Tilt) 234 0x15, 0x81,//Logical Minimum (-127) 235 0x25, 0x7F,//Logical Maximum (127) 236 0x95, 0x01,//Report Count (1) 237 0x75, 0x08,//Report Size (8) 238 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 239 240 0x09, 0x3E,//Usage (Y Tilt) 241 0x15, 0x81,//Logical Minimum (-127) 242 0x25, 0x7F,//Logical Maximum (127) 243 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 244 0xC0,//End Collection 245 0xC0,//End Collection 246 /*******************************Vendor-Defined 4-23*****************************************/ 247 0x06, 0x03,0xFF,/*Usage Page (Vendor-Defined 4)*/ 248 0x09, 0x000,/*Usage (Undefined)*/ 249 0xA1, 0x01,/*COLLECTION (Application)*/ 250 251 0x85, 0x0B,//Report ID (11) 252 0x15, 0x00,//LOGICAL_MINIMUM (0) 253 0x25, 0xFF,0x00,//LOGICAL_MAXIMUM (255) 254 0x09, 0x00,//Usage (Undefined) 255 0x75, 0x08,//REPORT_SIZE (8) 256 0x95, 0x3F,//Report Count (63) 257 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 258 0xC0//End Collection 259 }; 260 /*Interface 2 HID Report Descriptor */ 261 const uint8_t HID_driver_ReportDescriptor[HID_driver_SIZ_REPORT_DESC] = 262 { 263 /********************************Vendor-Defined 11**36*****************************************/ 264 0x06, 0x0A,0xFF,/*Usage Page (Vendor-Defined 11)*/ 265 0x09, 0x01,/*Usage (Vendor-Defined 1)*/ 266 0xA1, 0x01,/*COLLECTION (Application)*/ 267 268 0x85, 0x02,//Report ID (2)--------------------------驅動使用此report 269 0x09, 0x02,//Usage (Vendor-Defined 2) 270 0x15, 0x00,//LOGICAL_MINIMUM (0) 271 0x25, 0xFF,0x00,//LOGICAL_MAXIMUM (255) 272 0x75, 0x08,//REPORT_SIZE (8) 273 0x95, 0x09,//Report Count (9) 274 0x81, 0x02,//Input (Data,Var,Abs,NWrp,Lin,Pref,NNul,Bit) 275 276 0x09, 0x03,//Usage (Vendor-Defined 3) 277 0x75, 0x08,//REPORT_SIZE (8) 278 0x95, 0x07,//Report Count (7) 279 0x15, 0x00,//LOGICAL_MINIMUM (0) 280 0x25, 0xFF,0x00,//LOGICAL_MAXIMUM (255) 281 0x91, 0x02,//Output (Data,Var,Abs,NWrp,Lin,Pref,NNul,NVol,Bit) 282 283 0xC0,//End Collection 284 };
三、在usb_des.h 文件定義報告描述符的大小及定義reportdescriptor並屏蔽原來的Custom_HID不須要的定義3d
#define mouse_SIZ_REPORT_DESC 0x00B1 //0HID 報告描述符大小177BYTE #define pen_SIZ_REPORT_DESC 0x00ED //1HID 報告描述符大小237BYTE #define HID_driver_SIZ_REPORT_DESC 0x0024 //2HID 報告描述符大小177BYTE //報告描述符定義 extern const uint8_t mouse_ReportDescriptor[mouse_SIZ_REPORT_DESC]; extern const uint8_t pen_ReportDescriptor[pen_SIZ_REPORT_DESC]; extern const uint8_t HID_driver_ReportDescriptor[HID_driver_SIZ_REPORT_DESC];
四、重點修改usb_pro.h文件指針
4.1 新增:ONE_DESCRIPTOR XX_Report_Descriptor及ONE_DESCRIPTOR XX_Hid_Descriptor函數,去除原來Custom_HID的。
/************分別獲取3個HID的報告描述符****************/ ONE_DESCRIPTOR mouse_Report_Descriptor = //用於得到報告描述符 { (uint8_t *)mouse_ReportDescriptor, mouse_SIZ_REPORT_DESC }; ONE_DESCRIPTOR pen_Report_Descriptor = { (uint8_t *)pen_ReportDescriptor, pen_SIZ_REPORT_DESC }; ONE_DESCRIPTOR HID_driver_Report_Descriptor = { (uint8_t *)HID_driver_ReportDescriptor, HID_driver_SIZ_REPORT_DESC }; /************分別獲取3個HID的配置描述符中的HID描述****************/ //mouse_OFF_HID_DESC/pen_OFF_HID_DESC/HID_driver_OFF_HID_DESC //是HID描述在配置描述符中的偏移量 ONE_DESCRIPTOR mouse_Hid_Descriptor = { (uint8_t*)CustomHID_ConfigDescriptor + mouse_OFF_HID_DESC, CUSTOMHID_SIZ_HID_DESC }; ONE_DESCRIPTOR pen_Hid_Descriptor = { (uint8_t*)CustomHID_ConfigDescriptor + pen_OFF_HID_DESC, CUSTOMHID_SIZ_HID_DESC }; ONE_DESCRIPTOR HID_driver_Hid_Descriptor = { (uint8_t*)CustomHID_ConfigDescriptor + HID_driver_OFF_HID_DESC, CUSTOMHID_SIZ_HID_DESC };
4.2 XX_OFF_HID_DESC是HID描述符在usb_des.h文件中配置描述符函數CustomHID_ConfigDescriptor的偏移量
因此在usb_des.h 文件定義:
//ONE_DESCRIPTOR XX_Hid_Descriptor 偏移量定義
#define mouse_OFF_HID_DESC 0x12 //18
#define pen_OFF_HID_DESC 0x28 //43
#define HID_driver_OFF_HID_DESC 0x44 //68
4.3修改void CustomHID_Reset(void)函數中相關端點的定義,
void CustomHID_Reset(void) { /* Set CustomHID_DEVICE as not configured */ pInformation->Current_Configuration = 0; pInformation->Current_Interface = 0;/*the default Interface*/ /* Current Feature initialization */ pInformation->Current_Feature = CustomHID_ConfigDescriptor[7]; SetBTABLE(BTABLE_ADDRESS); /* Initialize Endpoint 0 */ SetEPType(ENDP0, EP_CONTROL); SetEPTxStatus(ENDP0, EP_TX_STALL); SetEPRxAddr(ENDP0, ENDP0_RXADDR); SetEPTxAddr(ENDP0, ENDP0_TXADDR); Clear_Status_Out(ENDP0); SetEPRxCount(ENDP0, Device_Property.MaxPacketSize); SetEPRxValid(ENDP0); /* Initialize Endpoint 1 IN 8 byte*/ SetEPType(ENDP1, EP_INTERRUPT); SetEPTxAddr(ENDP1, ENDP1_TXADDR); SetEPTxCount(ENDP1, 8); SetEPTxStatus(ENDP1, EP_TX_NAK); /* Initialize Endpoint 2 IN 10 byte*/ SetEPType(ENDP2, EP_INTERRUPT); SetEPTxAddr(ENDP2, ENDP2_TXADDR); SetEPTxCount(ENDP2, 10); SetEPTxStatus(ENDP2, EP_TX_NAK); /* Initialize Endpoint 3 IN 10 byte*/ SetEPType(ENDP3, EP_BULK); SetEPTxAddr(ENDP3, ENDP3_TXADDR); SetEPTxCount(ENDP3, 10); //設置發送的長度 SetEPTxStatus(ENDP3, EP_TX_NAK); //設置發送端點非應答 //SetEPRxStatus(ENDP3, EP_RX_DIS); //設置接受端點關閉 /* Initialize Endpoint 3 OUT 64 byte max */ SetEPType(ENDP3, EP_BULK); SetEPRxAddr(ENDP3, ENDP3_RXADDR); SetEPRxCount(ENDP3, 64); SetEPRxStatus(ENDP3, EP_RX_VALID); //SetEPTxStatus(ENDP3, EP_TX_DIS); /* Set this device to response on default address */ SetDeviceAddress(0); bDeviceState = ATTACHED; }
及usb_conf.h文件相關端點地址定義:
#define EP_NUM (3) //修改支持的端點數量by linxw /*-------------------------------------------------------------*/ /* -------------- Buffer Description Table -----------------*/ /*-------------------------------------------------------------*/ /* buffer table base address */ #define BTABLE_ADDRESS (0x00) /* EP0 */ /* rx/tx buffer base address */ #define ENDP0_RXADDR (0x40) #define ENDP0_TXADDR (0x80) /* EP1 */ /* tx buffer base address */ #define ENDP1_TXADDR (0xC0) //ENDP0_TXADDR+0x40開始 /* EP2 */ /* tx buffer base address */ #define ENDP2_TXADDR (0x100) //ENDP1_TXADDR+0x40開始 /* EP3 */ /* tx buffer base address */ #define ENDP3_TXADDR (0x140) //ENDP2_TXADDR+0x40開始 #define ENDP3_RXADDR (0x180)
4.4修改RESULT CustomHID_Data_Setup(uint8_t RequestNo相關HID配置
/******************************************************************************* * Function Name : CustomHID_Data_Setup * Description : Handle the data class specific requests. *這個函數對不一樣的接口進行區分,USBwIndex0反應出接口數量,不一樣接口返回不一樣的報告描述符 *第0接口:返回mouse相關的描述符 *第1接口:返回prn相關的描述符 *第2接口:返回driver相關的描述符 * Input : Request Nb. * Output : None. * Return : USB_UNSUPPORT or USB_SUCCESS. *******************************************************************************/ RESULT CustomHID_Data_Setup(uint8_t RequestNo) { uint8_t *(*CopyRoutine)(uint16_t); if (pInformation->USBwIndex != 0) return USB_UNSUPPORT; CopyRoutine = NULL; if ((RequestNo == GET_DESCRIPTOR) && (Type_Recipient == (STANDARD_REQUEST | INTERFACE_RECIPIENT)) && (pInformation->USBwIndex0 < 3)) { //在下面對3個接口進行區分 //CopyRoutine是指針函數,以指示運行哪一個函數 //須要構建6個函數 XX_GetReportDescriptor 和 XX_GetHIDDescriptor if (pInformation->USBwValue1 == REPORT_DESCRIPTOR) { //判斷 if (pInformation->USBwIndex0 == 0) { CopyRoutine = mouse_GetReportDescriptor; } else if (pInformation->USBwIndex0 == 1) { CopyRoutine = pen_GetReportDescriptor; } else if (pInformation->USBwIndex0 == 2) { CopyRoutine = HID_driver_GetReportDescriptor; } } else if (pInformation->USBwValue1 == HID_DESCRIPTOR_TYPE) { //判斷 if (pInformation->USBwIndex0 == 0) { CopyRoutine = mouse_GetHIDDescriptor; } else if (pInformation->USBwIndex0 == 1) { CopyRoutine = pen_GetHIDDescriptor; } else if (pInformation->USBwIndex0 == 2) { CopyRoutine = HID_driver_GetHIDDescriptor; } } } /* End of GET_DESCRIPTOR */ /*** GET_PROTOCOL, GET_REPORT, SET_REPORT ***/ //這部分看是否須要更改 else if ( (Type_Recipient == (CLASS_REQUEST | INTERFACE_RECIPIENT)) ) { switch( RequestNo ) { case GET_PROTOCOL: CopyRoutine = CustomHID_GetProtocolValue; break; case SET_REPORT: CopyRoutine = CustomHID_SetReport_Feature; Request = SET_REPORT; break; default: break; } } if (CopyRoutine == NULL) { return USB_UNSUPPORT; } pInformation->Ctrl_Info.CopyData = CopyRoutine; pInformation->Ctrl_Info.Usb_wOffset = 0; (*CopyRoutine)(0); return USB_SUCCESS; }
4.5以上CustomHID_Data_Setup函數須要構建6個函數:
在usb_prop.h增長函數的定義並去除無關的Custom_HID函數定義:
//新增函數定義
uint8_t *mouse_GetReportDescriptor(uint16_t Length);
uint8_t *pen_GetReportDescriptor(uint16_t Length);
uint8_t *HID_driver_GetReportDescriptor(uint16_t Length);
uint8_t *mouse_GetHIDDescriptor(uint16_t Length);
uint8_t *pen_GetHIDDescriptor(uint16_t Length);
uint8_t *HID_driver_GetHIDDescriptor(uint16_t Length);
在usb_proc.c定義:
/******************************************************************************* * Function Name : XX_GetReportDescriptor. * Description : Gets the HID report descriptor. * Input : Length * Output : None. * Return : The address of the configuration descriptor. *******************************************************************************/ uint8_t *mouse_GetReportDescriptor(uint16_t Length) { return Standard_GetDescriptorData(Length, &mouse_Report_Descriptor); } uint8_t *pen_GetReportDescriptor(uint16_t Length) { return Standard_GetDescriptorData(Length, &pen_Report_Descriptor); } uint8_t *HID_driver_GetReportDescriptor(uint16_t Length) { return Standard_GetDescriptorData(Length, &HID_driver_Report_Descriptor); } /******************************************************************************* * Function Name : XX_GetHIDDescriptor. * Description : Gets the HID descriptor. * Input : Length * Output : None. * Return : The address of the configuration descriptor. *******************************************************************************/ uint8_t *mouse_GetHIDDescriptor(uint16_t Length) { return Standard_GetDescriptorData(Length, &mouse_Hid_Descriptor); } uint8_t *pen_GetHIDDescriptor(uint16_t Length) { return Standard_GetDescriptorData(Length, &pen_Hid_Descriptor); } uint8_t *HID_driver_GetHIDDescriptor(uint16_t Length) { return Standard_GetDescriptorData(Length, &HID_driver_Hid_Descriptor); }
五、完成測試:
枚舉成功,but在bus hound下看到,每個HID的枚舉,主機PC發送set_idle。設備並無解析,出現stall pid錯誤,雖然不影響HID的使用,看着彆扭,因而查找了大量的文件,瞭解清楚,
最終,在固件庫usb_proc.c文件裏,修改如下函數,
出現的stall pid現象:
CustomHID_NoData_Setup:資料下載連接https://download.csdn.net/download/weixin_43245044/11052195
RESULT CustomHID_NoData_Setup(uint8_t RequestNo) { if ((Type_Recipient == (CLASS_REQUEST | INTERFACE_RECIPIENT)) && (RequestNo == SET_PROTOCOL)) { return CustomHID_SetProtocol(); } //增長對PC端set_idle 請求的迴應,不回覆---by linxw if ((Type_Recipient == (CLASS_REQUEST | INTERFACE_RECIPIENT)) && (RequestNo == SET_IDLE)) { return USB_SUCCESS; } else { return USB_UNSUPPORT; } }