《使枚举成功的USB设备成为WINUSB设备》
1. 将设备枚举为WINUSB设备
1.1 使设备能获取字符串描述符
1、 确保devicedescriptor中字符串index不为0。如图所示,红色框中部分不能设置为0,若设置为0则Host不会发送获取字符串的命令。
uint8_tUSBDeviceDesc[USB_LEN_DEV_DESC] =
{
0x12, /*bLength: 18bit*/
USB_DESC_TYPE_DEVICE, /*bDescriptorType: 0x02*/
0x00, /*bcdUSB */
0x02,
0x00, /*bDeviceClass*/
0x00, /*bDeviceSubClass*/
0x00, /*bDeviceProtocol*/
USB_MAX_EP0_SIZE, /*bMaxPacketSize: 64bit*/
0x37, /*低位idVendor*/
0x05, /*高位idVendor*/
0x21, /*低位idVendor*/
0x43, /*高位idVendor*/
0x00, /*bcdDevice rel. 2.00*/
0x02,
USBD_IDX_MFC_STR, /*Index of manufacturer string USBD_IDX_MFC_STR*/
USBD_IDX_PRODUCT_STR, /*Index of product stringUSBD_IDX_PRODUCT_STR*/
USBD_IDX_SERIAL_STR, /*Index of serial number stringUSBD_IDX_SERIAL_STR*/
USBD_MAX_NUM_CONFIGURATION /*bNumConfigurations 固定为1,因为只有一个配置描述符*/
};
其中:
#define USBD_IDX_MFC_STR 0x01
#define USBD_IDX_PRODUCT_STR 0x02
#define USBD_IDX_SERIAL_STR 0x03
2、 根据索引值发送字符串描述符
1、 判断获取的标准命令wValue字段部分低8位。
2、 发送字符串描述符。其格式如下表:
其中bLength=字符串描述符的长度为原字符串长度*2+2,bDescriptorType固定为0x03,bString中的内容是unicode编码(就是在ASCII码前面加上0x00即可)。
例如:若想要的字符串为"LSQ",那么其字符串描述符应为:
Uint8_tUSBManufactoryString[USB_LEN_MAU_STRING]=
{
USB_LEN_MAU_STRING, // 这里是0x08
0x03,
0x4C, //L
0x00,
0x53, //S
0x00,
0x51, //Q
0x00
}
1.2 处理获取操作系统字符串描述符的标准命令
当上文提到的字符串描述符正确上传到主机上时(可以用USB monitor)检测到。此时Host会发送获取操作系统字符串描述符(OS String Descriptor)。它包含OS string descriptor和OS feature descriptors。此时按照下文所述步骤操作:
1、主机发送要求获取索引值为0XEE的字符串(即OSString Descriptor)的命令。其标准请求命令格式为:
bmRequestType |
bRequest |
wValue |
wIndex |
wLength |
Data |
1000 0000B |
GET_DESCRIPTOR |
0x03EE |
0x0000 |
0x12 |
Returned String |
其中:
1、 GET_DESCRIPTOR为0x03。
2、设备发送OS StringDescriptor。
1、OS String Descriptor格式。例如:
Field |
Length (Bytes) |
Value |
Description |
bLength |
1 |
0x12 |
Length of the descriptor |
bDescriptorType |
1 |
0x03 |
Descriptor type |
qwSignature |
14 |
‘MSFT100’ |
Signature field |
bMS_VendorCode |
1 |
Vendor-specific |
Vendor code |
bPad |
1 |
0x00 |
Pad field |
其中:
1、1.0版本的OS StringDescriptor的qwSignature字段必须设为‘MSFT100’(0x4D00 0x5300 0x4600 0x5400 0x3100 0x3000 0x3000)。
2、bMS_VendorCode字段是自定义数字。
例如:
uint8_tUSBD_OS_StringDesc[USB_LEN_OS_STRING_DESC]=
{
USB_LEN_OS_STRING_DESC, // 0X12
USB_DESC_TYPE_DEVICE, // 0X03
0x4D, // M
0x00,
0x53, // S
0x00,
0x46, // F
0x00,
0x54, // T
0x00,
0x31, // 1
0x00,
0x30, // 0
0x00,
0x30, // 0
0x00,
0x01, // 自定义数字即可
0x00
};
3、Host发送要求获取OS FeatureDescriptor的标准命令请求,SETUP包内容为:
bmRequestType |
bRequest |
wValue |
wIndex |
wLength |
Data |
1100 0000B |
GET_MS_DESCRIPTOR |
Interface |
Feature Index |
Length |
Returned Descriptor |
其中:
1、 GET_MS_DESCRIPTOR为OS String Descriptor中的bMS_VendorCode字段。
3、 设备发送OS FeatureDescriptor。
1、 OS Feature Descriptor格式为:
OS FeatureDescriptor包含两个部分:
i. Header Section
Offset |
Field |
Size (bytes) |
Type |
Description |
0 |
dwLength |
4 |
DWORD |
The length, in bytes, of the complete extended compat ID descriptor |
4 |
bcdVersion |
2 |
BCD |
The descriptor’s version number, in binary coded decimal (BCD) format |
6 |
wIndex |
2 |
WORD |
An index that identifies the particular OS feature descriptor |
8 |
bCount |
1 |
BYTE |
The number of custom property sections |
9 |
RESERVED |
7 |
BYTEs |
Reserved |
其中:
1、 若操作系统描述符版本为1.00,那么bcdVersion固定为0x0100。
2、 wIndex设定为0x04.
3、 bCount表示有几个Function Section。
ii. Function Section
Offset |
Field |
Size (bytes) |
Type |
Description |
0 |
bFirstInterfaceNumber |
1 |
BYTE |
The interface or function number |
1 |
RESERVED |
1 |
BYTE |
Reserved |
2 |
compatibleID |
8 |
BYTEs |
The function’s compatible ID |
10 |
subCompatibleID |
8 |
BYTEs |
The function’s subcompatible ID |
18 |
RESERVED |
6 |
BYTEs |
Reserved |
Note: The offsets in this table are given from the beginning of the section. To calculate the offset of a field from the beginning of the entire descriptor, add the length of the header section and the lengths of any function sections that precede this section to the value in the table. |
其中:
1、 bFirstInterfaceNumber字段是端口号,这里我们设为0。
2、 第一个RESERVED部分为0x01,第二个RESERVED部分全为NULLS(即0x00)。
3、 compatibleID字段为兼容性ID,这里我们要设为WINUSB。不够8字节的时候需要用NULL补齐8字节。
4、 subCompatibleID字段在这里我们可以设为8个NULL。
例如:
uint8_tUSB_OS_FEATURE_STRING[USB_COMPID_LENGTH]=
{
// header 9bit
USB_COMPID_LENGTH,
0x00,
0x00,
0x00,
0x00, //低位bcdVersion
0x01, //高位bcdVersion
0x04, //index of compat ID descriptors
0x00,
0x01, //1个function
// reserved 7bit
0x00,
0x00,
0x00,
0x00,
0x00,
0x00,
0x00,
// function
// 2bit
0x00, //端点0
0X01,
// compatibleID 8bit
0x57, //W
0x49, //I
0x4E, //N
0X55, //U
0x53, //S
0x42, //B
0x00,
0x00,
// subCompatibleID 8bit
0x00,
0x00,
0x00,
0x00,
0x00,
0x00,
0x00,
0x00,
// RESERVED 6bit
0x00,
0x00,
0x00,
0x00,
0x00,
0x00
};
2. 获取操作系统描述符相关文档
1、 从这个网址上获取:【https://msdn.microsoft.com/library/windows/hardware/gg463179】
2、 如图点击“我接受”后会在右边弹出“下载”按钮。