ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

关于USB的一些基础概念

2022-07-09 11:07:58  阅读:181  来源: 互联网

标签:USB uint8 接口 概念 描述符 关于 端点 设备


1、USB模式

1.单模式

(1) host only, 使用于内部互联芯片USB做host的情况

(2) device only, 使用于内部互联芯片USB做device的情况

2. otg模式

(1) typec OTG: 基于typec接口 + cclogic的设计方案

(2) phy OTG: 基于GPIO实现USB模式的切换的设计方案

 

2、总线架构

主从结构,总线上只能有一个主机,依靠hub向下扩展,一条总线最多可以接127个设备。所有USB传输,都是由主机发起,设备device没有主动通知主机的能力

2.1 Endpoint(端点)

 看上图,每个USB 设备都有一个唯一的设备地址,设备地址是设备连接主机时,由主机分配的,主机依靠设备地址与usb device通信;

但在设备内部会被分的更细,设备会有很多端点,每个端点都有唯一的端点号,这个是设计设备的时候给定的(代码里写好,其实就是配寄存器),比如我们之前写的通过bulk裸传liveview数据的功能,就用到了某个端点。注意其中端点0比较特殊,它是用来进行对设备枚举和控制的

对于端点的进一步理解,可以看一下端点描述符,所谓描述符,可以理解成描述端点的结构体,我们直接看下结构定义好了:

 typedef struct _USB_ENDPOINT_DESCRIPTOR_
{
    BYTE        bLength,
    BYTE        bDescriptorType,
    BYTE        bEndpointAddress,
    BYTE        bmAttributes,
    WORD      wMaxPacketSize,
    BYTE        bInterval
}USB_ENDPOINT_DESCRIPTOR;

各变量具体释义如下:
bLength : 描述符大小.固定为0x07.
bDescriptorType : 接口描述符类型.固定为0x05.
bEndpointType : USB设备的端点地址.Bit7,方向,对于控制端点可以忽略,1/0:IN/OUT.Bit6-4,保留.BIt3-0:端点号.
bmAttributes : 端点属性.Bit7-2,保留.BIt1-0:00控制,01同步,02批量,03中断.
wMaxPacketSize : 本端点接收或发送的最大信息包大小(说明最大是 2^16 Bytes = 64KB)
bInterval : 轮训数据传送端点的时间间隔.对于批量传送和控制传送的端点忽略.对于同步传送的端点,必须为1,对于中断传送的端点,范围为1-255。

 2.2 Interface

一个接口(interface)含有0个或者多个端点(endpoint),端点是USB通信的最基本形式。看一下接口的描述符定义;

#pragma data_alignment=1    //对齐方式为Byte
typedef struct _USB_Desc_Interface_t {
    uint8_t bLength;                // 固定值9B
    uint8_t bDescriptorType;        // 固定值Interface(0x04)
    uint8_t bInterfaceNum;          // 接口索引号
    uint8_t bAlternateSetting;      // 备用接口号
    uint8_t bNumberEndpoints;       // 端点数量
    uint8_t bInterfaceClass;        // 接口类型
    uint8_t bInterfaceSubclass;     // 接口子类型
    uint8_t bInterfaceProtocol;     // 接口协议
    uint8_t bInterfaceStringIndex;  // 接口名称的字符串索引号
}USB_Desc_Interface_t;

要理解接口的含义,我们需要看一下描述符集的层次结构:

 

 从下往上看:

  1. 一个USB设备只有一个设备描述符
  2. 一个设备描述符包含一个或多个配置描述符
  3. 一个配置描述符包含一个或多个接口描述符
  4. 一个接口描述符包含一个或多个端点描述符

接口描述符中,有一个比较重要的属性叫做bInterfaceClass 接口类型,其定义参考USB IF,这里摘一段官网的解释

USB defines class code information that is used to identify a device’s functionality and to nominally load a device driver based on that functionality. The information is contained in three bytes with the names Base Class, SubClass, and Protocol. (Note that ‘Base Class’ is used in this description to identify the first byte of the Class Code triple. That terminology is not used in the USB Specification). There are two places on a device where class code information can be placed. One place is in the Device Descriptor, and the other is in Interface Descriptors. Some defined class codes are allowed to be used only in a Device Descriptor, others can be used in both Device and Interface Descriptors, and some can only be used in Interface Descriptors. The table below shows the currently defined set of Base Class values, what the generic usage is, and where that Base Class can be used (either Device or Interface Descriptors or both).

这句话是什么意思呢,就是说接口类型这个属性是用来识别设备功能的,同时host也可以据此加载对应的驱动。有两个地方都可以包含这个接口类型,一个地方就是我们正在看的接口描述符,另外一个地方就是设备描述符。其中有一些class codes是只给设备描述符用的,有一些是只给接口描述符用的,剩下的则是二者都可使用,比如网站上列出了下面的list:

对照一下设备描述看:

typedef struct _USB_Desc_Device_t {
    uint8_t   bLength;                  // 固定值18B
    uint8_t   bDescriptorType;          // 固定值Device(0x01)
    uint16_t  wBcdUSB;                  // USB Spec版本
    uint8_t   bDeviceClass;             // 设备类型
    uint8_t   bDeviceSubClass;          // 设备子类型
    uint8_t   bDeviceProtocol;          // 协议类型
    uint8_t   bMaxPacketSize0;           // EP0的最大包长度
    uint16_t  wIdVendor;                // 厂商ID
    uint16_t  wIdProduct;               // 产品ID
    uint16_t  wBcdDevice;               // 设备软件版本
    uint8_t   bStringIndexManufacturer; // 厂商名称字符串索引号
    uint8_t   bStringIndexProduct;      // 产品名称字符串索引号
    uint8_t   bStringIndexSerialNumber; // 序列号索字符串引号
    uint8_t   bNumConfigurations        // 配置数量>=1
}USB_Desc_Device_t;

里面也有设备类型,映证了上面的说法。这里注意一个比较特殊的值,如果说设备类型是00h, 则说明class code要到接口描述符中去获取。

还剩下一个配置描述符,如何理解配置描述呢?

#pragma data_alignment=1    //对齐方式为Byte
typedef struct _USB_Desc_Configuration_t {
    uint8_t   bLength;                 // 固定值9B
    uint8_t   bDescriptorType;         // 固定值Configuration(0x02)
    uint16_t  wTotalConfigurationSize; // 配置集合的总大小
    uint8_t   bTotalInterfaces;        // 配置集合的接口数量
    uint8_t   bConfigurationNumber;    // 当前配置的序号(从1开始)
    uint8_t   bConfigurationStrIndex;  // 配置名称的字符串索引号
    uint8_t   bConfigAttributes;       // 配置集合的属性
    uint8_t   bMaxPowerConsumption;    // 最大供电电流,单位是2mA
}USB_Desc_Configuration_t;

// 配置集合的属性
typedef struct _bConfigAttributes_t{
    uint8_t   b5reserved:5;            // 保留置0
    uint8_t   b1RemoteWakeup:1;        // 置1表示支持远程唤醒
    uint8_t   b1Selfpowerd:1;          // 置1表示支持自己供电
    uint8_t   b1reserved:1;            // 保留置1
}bConfigAttributes_t;

这个时候我们大概有了一个这样的认知,一个usb设备,有多个配置,这些配置本身的描述符不重要,重要的是这些配置里面包含了多个interface,

每个interface对应着设备的实际功能,比如一个眼镜的usb口,它可以被枚举成一个mass storage设备,它也可以被枚举成一个video 播放器等等,如果有cc,它还可以变为host 去枚举别的设备

 

标签:USB,uint8,接口,概念,描述符,关于,端点,设备
来源: https://www.cnblogs.com/Arnold-Zhang/p/16326955.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有