【极客技术传送门】 : https://blog.csdn.net/Engineer_LU/article/details/135149485
USB2.0的结构简洁,VCC, D+, D-, GND通信.
主机的两个下拉电阻阻值为15K,从机的D+ D-上拉电阻为1.5K
通讯依靠D+,D-作为差分
对于低速,全速设备USB通信四种状态,逻辑0与逻辑1和JK状态不加以区分
J | K | SE0 | SE1 | |
---|---|---|---|---|
D + | 0 | 1 | 0 | 1 |
D - | 1 | 0 | 0 | 1 |
对于高速设备,做了8b/10b编码,把逻辑0与逻辑1和JK状态区分开来
{ K, D[7], D[6], D[5], D[4], D[3], D[2], D[1], J, D[0] }
下图为USB2.0的结构 :
模式 | 上拉电阻接入 (1.5K) | 速度 |
---|---|---|
低速 | D- | 1.5M |
全速 | D+ | 12M |
高速 | D+ | 480M |
模式 | 上拉电阻接入 (1.5K) |
---|---|
拔出 | 无 |
描述符前言 :
- 在写描述符之前,这里将USB意义简述一下。
- USB协议总是主机发起通信,如果从机的内容比较多,那么主机该如何与从机的某个局部信息进行交互呢?
- 无论从机有多少信息,我们把它分而治之不就可以了吗,就像一省有N市,一市有N镇,一镇有N村,假如你想了解某个人的信息,那么通过省市镇村就可以找到对方进行交互,USB协议里也是一样,逐层解析。
- 所以诞生了设备描述符,配置描述符,接口描述符,端点描述符,报告描述符,特殊描述符,字符串描述符,各描述符都有自己的数据结构,以下详述了各描述符意义。
设备描述符总结 :
- 设备描述符是设备插入 USB 总线时被主机系统主动请求的第一个描述符。
- 主机系统通过读取设备描述符可以获取设备的基本特性,从而为设备进行正确的配置和管理。
- 设备描述符是 USB 设备描述符的核心组成部分,提供了主机系统获取关于设备基本信息的入口,有助于主机正确识别、配置和与设备进行通信。
配置描述符总结 :
- 配置描述符提供了主机系统有关设备配置的基本信息。
- 一个 USB 设备可以有一个或多个配置,每个配置可以包含一个或多个接口,每个接口可以包含一个或多个端点。
- 主机系统通过读取配置描述符,能够了解设备的整体结构和提供的功能,从而为设备进行正确的配置和管理。
- 配置描述符是 USB 设备描述符的关键组成部分,有助于主机系统正确识别、配置和与设备进行通信。
接口描述符总结 :
- 接口描述符对于主机系统正确识别和配置设备的每个接口非常重要。
- 主机系统通过读取接口描述符可以了解设备提供了多少个接口,每个接口的功能是什么,以及每个接口上有多少个端点。
- 接口描述符是 USB 设备描述符的一部分,用于提供关于每个接口的基本信息,帮助主机系统正确识别、配置和与设备进行通信。
端点描述符总结 :
- 端点描述符提供了主机系统关于设备上每个端点的详细信息,主机系统根据这些信息来正确配置和管理数据传输。
- 不同类型的端点有不同的用途,例如控制端点用于设备和主机之间的基本控制和配置,而同步和异步端点则用于数据传输等。
- 每个 USB 接口可以包含多个端点,其中包括一个控制端点(Endpoint 0),用于设备和主机之间的基本通信。
- 端点描述符通常跟随在接口描述符之后,为主机系统提供有关每个端点的配置信息。
- 端点描述符是 USB 设备描述符的关键组成部分,提供了主机系统关于设备上每个端点的详细信息,有助于正确配置和管理数据传输。
报告描述符总结 :
- 报告描述符是在 HID 类别中定义的,典型的 HID 设备如键盘或鼠标通常会包含一个或多个报告描述符。
- 主机系统通过读取报告描述符可以了解 HID 设备生成数据报告的结构,从而正确解析和处理来自 HID 设备的数据。
- 报告描述符在 HID 设备中起到了定义设备数据报告结构的关键作用,它是 USB 设备描述符的一部分,用于描述 HID 设备生成的数据报告的格式和内容。
String Descriptor(字符串描述符): USB 设备可以包含多个字符串描述符,用于提供设备的可读文本信息,如制造商名称、产品名称、序列号等。
Interface Association Descriptor(接口关联描述符): 这是一种辅助描述符,用于关联多个接口。例如,一个设备可能同时提供音频输入和输出,这两个功能可能被关联在一起。
Endpoint Companion Descriptor(端点伴随描述符): 在 USB 3.0 中引入,提供了关于端点的额外信息,如是否支持超速传输等。
BOS (Binary Object Store) Descriptor(二进制对象存储描述符): 用于提供设备的固件升级和其他二进制对象的信息。
Device Capability Descriptor(设备能力描述符): 提供了关于设备支持的一些特殊功能和能力的信息,如 USB PD(USB Power Delivery)的支持等。
特殊描述符总结 :
- 一般HID,CDC设备会带有特殊描述符,补充描述
- 这些描述符可能是标准描述符,也可能是设备特定的描述符。
- 特殊描述符的存在使得设备能够提供额外的信息,或者支持一些规范中未明确定义的功能。
- 需要查阅设备的技术文档或者 USB 设备的特定规范以了解特殊描述符的具体细节和用途,因为它们的内容和用途在不同类型的设备中可能有很大的差异。
语言标识符描述符(Language ID Descriptor): 这是一种特殊的字符串描述符,用于指示设备支持的语言。语言标识符描述符的索引为零,它的值是一个语言标识符列表,表示设备支持的语言。
字符串描述符: 每个字符串描述符包含了一个 UTF-16 编码的字符串,用于表示特定的信息,如制造商名称、产品名称、序列号等。字符串描述符的索引值是非零的,每个索引值对应一种特定的字符串。
字符串描述符总结 :
- 字符串描述符的格式包括一个字节的长度信息,后面是一个或多个包含 UTF-16 编码的字符。
- USB 规范规定字符串描述符的字符编码必须为 UTF-16LE(Little Endian)。
- 例如,如果要获取设备的制造商名称,主机系统可以向设备发送请求,指定索引值为设备制造商名称的字符串描述符,设备会回复一个包含制造商名称的字符串描述符。
- 字符串描述符提供了对设备信息的人类可读访问,有助于用户和操作系统正确识别和管理连接到系统的 USB 设备。
- 字符串描述符是 USB 设备描述符中的一种类型,用于提供设备的人类可读的文本信息。
USB协议里从机不会主动发起通信,因为主机很多事情做,总线却只有一个,所以当主机 “忙完”, 就会主动向从机发起通信,通信过程包含三种情况。
主机一开始请求过程会发送令牌包(TOKEN),请求中声明有数据要传输则有数据过程(长度描述不为0),最后由从机发起状态过程,结束本次通信。
如果主机向从机获取数据,那么主机获取到数据后,状态过程由主机发起结束。
HID设备的数据在报告描述符内描述数据结构,然后就可以通过传输包来交互数据,报告描述符网上很多,若是不需要深入了解,可以直接用现成的。
const uint8_t Virtual_Com_Port_DeviceDescriptor[] =
{
0x12, /* bLength */
USB_DEVICE_DESCRIPTOR_TYPE, /* bDescriptorType */
0x00,
0x02, /* bcdUSB = 2.00 */
0x02, /* bDeviceClass: CDC */
0x00, /* bDeviceSubClass */
0x00, /* bDeviceProtocol */
0x40, /* bMaxPacketSize0 */
0x85,
0x06, /* idVendor = 0x0685 */
0x40,
0x57, /* idProduct = 0x7540 */
0x00,
0x02, /* bcdDevice = 2.00 */
1, /* Index of string descriptor describing manufacturer */
2, /* Index of string descriptor describing product */
3, /* Index of string descriptor describing the device's serial number */
0x01 /* bNumConfigurations */
};
const uint8_t Virtual_Com_Port_ConfigDescriptor[] =
{
/*Configuration Descriptor*/
0x09, /* bLength: Configuration Descriptor size */
USB_CONFIGURATION_DESCRIPTOR_TYPE, /* bDescriptorType: Configuration */
VIRTUAL_COM_PORT_SIZ_CONFIG_DESC, /* wTotalLength:no of returned bytes */
0x00,
0x02, /* bNumInterfaces: 2 interface */
0x01, /* bConfigurationValue: Configuration value */
0x00, /* iConfiguration: Index of string descriptor describing the configuration */
0xC0, /* bmAttributes: self powered */
0x32, /* MaxPower 0 mA */
/*Interface Descriptor*/
0x09, /* bLength: Interface Descriptor size */
USB_INTERFACE_DESCRIPTOR_TYPE, /* bDescriptorType: Interface */
/* Interface descriptor type */
0x00, /* bInterfaceNumber: Number of Interface */
0x00, /* bAlternateSetting: Alternate setting */
0x01, /* bNumEndpoints: One endpoints used */
0x02, /* bInterfaceClass: Communication Interface Class */
0x02, /* bInterfaceSubClass: Abstract Control Model */
0x01, /* bInterfaceProtocol: Common AT commands */
0x00, /* iInterface: */
/*Header Functional Descriptor*/
0x05, /* bLength: Endpoint Descriptor size */
0x24, /* bDescriptorType: CS_INTERFACE */
0x00, /* bDescriptorSubtype: Header Func Desc */
0x10, /* bcdCDC: spec release number */
0x01,
/*Call Management Functional Descriptor*/
0x05, /* bFunctionLength */
0x24, /* bDescriptorType: CS_INTERFACE */
0x01, /* bDescriptorSubtype: Call Management Func Desc */
0x00, /* bmCapabilities: D0+D1 */
0x01, /* bDataInterface: 1 */
/*ACM Functional Descriptor*/
0x04, /* bFunctionLength */
0x24, /* bDescriptorType: CS_INTERFACE */
0x02, /* bDescriptorSubtype: Abstract Control Management desc */
0x02, /* bmCapabilities */
/*Union Functional Descriptor*/
0x05, /* bFunctionLength */
0x24, /* bDescriptorType: CS_INTERFACE */
0x06, /* bDescriptorSubtype: Union func desc */
0x00, /* bMasterInterface: Communication class interface */
0x01, /* bSlaveInterface0: Data Class Interface */
/*Endpoint 2 Descriptor*/
0x07, /* bLength: Endpoint Descriptor size */
USB_ENDPOINT_DESCRIPTOR_TYPE, /* bDescriptorType: Endpoint */
0x82, /* bEndpointAddress: (IN2) */
0x03, /* bmAttributes: Interrupt */
VIRTUAL_COM_PORT_INT_SIZE, /* wMaxPacketSize: */
0x00,
0xFF, /* bInterval: */
/*Data class interface descriptor*/
0x09, /* bLength: Endpoint Descriptor size */
USB_INTERFACE_DESCRIPTOR_TYPE, /* bDescriptorType: */
0x01, /* bInterfaceNumber: Number of Interface */
0x00, /* bAlternateSetting: Alternate setting */
0x02, /* bNumEndpoints: Two endpoints used */
0x0A, /* bInterfaceClass: CDC */
0x00, /* bInterfaceSubClass: */
0x00, /* bInterfaceProtocol: */
0x00, /* iInterface: */
/*Endpoint 3 Descriptor*/
0x07, /* bLength: Endpoint Descriptor size */
USB_ENDPOINT_DESCRIPTOR_TYPE, /* bDescriptorType: Endpoint */
0x03, /* bEndpointAddress: (OUT3) */
0x02, /* bmAttributes: Bulk */
VIRTUAL_COM_PORT_DATA_SIZE, /* wMaxPacketSize: */
0x00,
0x00, /* bInterval: ignore for Bulk transfer */
/*Endpoint 1 Descriptor*/
0x07, /* bLength: Endpoint Descriptor size */
USB_ENDPOINT_DESCRIPTOR_TYPE, /* bDescriptorType: Endpoint */
0x81, /* bEndpointAddress: (IN1) */
0x02, /* bmAttributes: Bulk */
VIRTUAL_COM_PORT_DATA_SIZE, /* wMaxPacketSize: */
0x00,
0x00 /* bInterval */
};
这里通过一个USB虚拟串口的CDC设备以代码形式展示,上面两个数组分别是设备描述符 和 配置描述符,其中设备描述符可以看到描述了关于USB协议2.0,属于CDC设备,VID,PID信息,配置描述符描述了接口描述符的数据结构,描述了端点描述符的结构,几个端点描述符分别用了中断传输,批量传输方式通信。
对于自带了USB外设的芯片,内部USB模块集成了串行接口控制器(SIE)、定时器、分组缓冲器接口、端点相关寄存器、控制寄存器和中断寄存器等部分组成,所以从机只需要把市面上USB的c文件h文件移植,移植后修改描述符,就可以对端点进行通信了。
USB协议细节较多,后续持续补充内容。
个人风格秉承深入浅出,简洁风格描述,谢谢观看。
技术交流QQ群 : 745662457
群内专注 - 问题答疑,技术研究
图片资源本人在网上下载,若有侵权行为,请告知,本人会立刻删除