Fork me on GitHub

USB协议详解第8讲(USB描述符-字符串和语言ID描述符)

1.字符串描述符相关概念

字符串描述符:首先,字符串描述符就是用字符串描述一个设备的一些属性,毕竟人能看懂的是字符,而不是十六进制,描述的属性包括设备厂商名字、产品名字、产品序列号、各个配置名字、各个接口名字,还有就是由我们用户自己定义的字符串,说白了就是起名字,让人们一看就知道这个设备是什么设备,字符串描述符对于设备来说是可选的

语言ID描述符:给大家明确一点,其实语言ID描述符也是字符串描述符,它比较特殊,是用来告诉主机其他字符串描述符里面的字符串都支持哪国家语言,因为USB标准全球都在用,字符串的显示形式也是各种各样。

主机需要先获取语言ID描述符确定都用哪些编码,才能正确解析后续得到的字符串描述符。再次说明,语言ID描述符和字符串描述符是一起出现的,因为只有确定了用什么语言,才能读懂后面的字符串。

2.语言ID描述符组成、详解、代码

(1)语言ID描述符组成

(2)语言ID描述符详解

1.bLength

描述符长度,这里的长度不确定,有可能会指示主机需要支持多国语言;

2.bDescriptorType

描述符类型,语言ID描述符也是字符串述符,类型为0x03;

3.wLANGID[0]

要支持的语言ID号,从USB_LANGIDs.pdf这个文档中查询,我也没有下载,大家可以去搜索查询,这里截取了一张图,其实我们用的最多就是标红的两种编码

4.wLANGID[n]

有可能会支持多种语言,我们这里先只支持一种,支持U.S English。

(3)语言ID描述符STM32代码

/* USB String Descriptors (optional) */
const uint8_t CustomHID_StringLangID[CUSTOMHID_SIZ_STRING_LANGID] =
{
    CUSTOMHID_SIZ_STRING_LANGID,
    USB_STRING_DESCRIPTOR_TYPE,
    0x09,
    0x04
}; /* LangID = 0x0409: U.S. English */

3.字符串描述符索引剖析

我们前面学过设备描述符、配置描述符、接口描述符,里面有各种字符串描述符索引项,大家肯定有疑惑不知道里面设置为多少,为什么厂商字符串索引、产品字符串索引、产品序列号字符串描述符索引规定为1、2、3等等。

在这里给大家解释下,其实索引号0是给语言ID字符串描述符的,主机必须先获取语言ID字符串描述符才能知道是哪国语言。所以设备如果要实现字符串描述符主机请求的响应,就必须先实现语言ID字符串描述符,当主机使用GET_DESCRIPTOR请求字符串描述符并且索引值为0时,设备必须返回语言ID字符串描述符(记住这里是必须)。

其它索引号也是主机规定的,主机请求索引号为1的字符串描述符,主机收到设备返回的字符串以后就认为是对厂商的字符串说明,设备你如果返回其它的字符串就是不按套路出牌,主机就会显示错位,比如会把厂商字符串显示到产品显示那块去。

如果设备不支持厂商字符串描述符、产品字符串描述符、产品序列号字符串描述符、配置字符串描述符、接口字符串描述符,则对应地方索引应该被设置为0,如下图几处地方设置为0即可。

4.字符串描述符组成、详解、代码

(1)字符串描述符组成

(2)字符串描述符详解

1.bLength

描述符长度,这里的长度不确定,因为字符串多长不定;

2.bDescriptorType

描述符类型,字符串描述符类型为0x03;

3.bString

UNICODE编码的字符串

(3)字符串描述符STM32代码

ONE_DESCRIPTOR String_Descriptor[4] =
{
    // index = 0;
    {(uint8_t*)CustomHID_StringLangID, CUSTOMHID_SIZ_STRING_LANGID},
    // index = 1;
    {(uint8_t*)CustomHID_StringVendor, CUSTOMHID_SIZ_STRING_VENDOR},
    // index = 2;
    {(uint8_t*)CustomHID_StringProduct, CUSTOMHID_SIZ_STRING_PRODUCT},
    // index = 3;
    {(uint8_t*)CustomHID_StringSerial, CUSTOMHID_SIZ_STRING_SERIAL}
};
 
const uint8_t CustomHID_StringVendor[CUSTOMHID_SIZ_STRING_VENDOR] =
{
    CUSTOMHID_SIZ_STRING_VENDOR, /* Size of Vendor string */
    USB_STRING_DESCRIPTOR_TYPE,  /* bDescriptorType*/
    // Manufacturer: "STMicroelectronics" 
    'M', 0, 'y', 0, 'U', 0,'S', 0,'B', 0, '_', 0, 'H', 0,'I',0,'D',0
};
 
const uint8_t CustomHID_StringProduct[CUSTOMHID_SIZ_STRING_PRODUCT] =
{
    CUSTOMHID_SIZ_STRING_PRODUCT,          /* bLength */
    USB_STRING_DESCRIPTOR_TYPE,        /* bDescriptorType */
    'B', 0, 'y', 0, ' ', 0, 'v', 0, 'i', 0, 'e', 0,'w',0,'t',0,'o',0,'o',0,'l',0
};
uint8_t CustomHID_StringSerial[CUSTOMHID_SIZ_STRING_SERIAL] =
{
    CUSTOMHID_SIZ_STRING_SERIAL,           /* bLength */
    USB_STRING_DESCRIPTOR_TYPE,        /* bDescriptorType */
    'x', 0, 'x', 0, 'x', 0,'x', 0,'x', 0, 'x', 0, 'x', 0
};
posted @ 2024-08-13 21:16  yooooooo  阅读(8)  评论(0编辑  收藏  举报