精华内容
下载资源
问答
  • USB接口的开发过程中,对于工程师来说还是会遇到这样或那样的问题,如何提高调试效率,缩短研发周期,就需要一种调试测试工具——USB协议分析仪USB协议分析仪  USB协议分析仪是协议层的分析工具,是测试设备...

      在现代电子设备中,越来越多的使用USB接口,不仅因为其使用方便,即插即拔,更因为其价格低廉,协议开放,而广泛使用在各种电子设备上,并且已经发展为不可缺少的一种接口形式。但USB接口的开发过程中,对于工程师来说还是会遇到这样或那样的问题,如何提高调试效率,缩短研发周期,就需要一种调试测试工具——USB协议分析仪。

    USB协议分析仪

         USB协议分析仪是协议层的分析工具,是测试设备的一种。对于USB这种高速串行总线来说,仅仅进行物理层测试是远远不够的,由于在高低电平中寓含着丰富的指令,传递着大量信息。所以对于USB传输协议就需要专用的USB协议分析仪来分析测试,USB协议分析仪是按照标准的USB协议来分解数据,将包含有用信息的数据提取出来,并解释这些数据的含义。随着设备之间传递数据速度的不断提高,越来越多的高速串行总线被使用,如SATASASEthernetFC等等,这些高速串行总线也同样有其协议分析工具。

    为了让读者更好的了解USB协议分析仪的功能与用途,本文列举一个调试USB通信的小例子。

    实验环境

    如图所示,左侧计算机安装USB协议分析仪软件,加上USB协议分析仪主机构成USB协议分析系统。DE2实验板作为USB设备,右侧计算机安装应用程序对DE2进行操作。我们主要关心安装有应用程序的计算机与DE2实验板之间的USB通信是否正常,并且希望了解这个通信过程是怎样完成的。

    DE2实验板是教学过程中使用的开发板,针对USB通信接口部分有一片接口控制芯片,可通过加载固件程序控制USB数据传输,对于USB开发工程师来说,编写固件程序是实现USB通信的重要部分,但很难验证固件程序是否正确,是否按照工程师的意愿执行。在PC端安装有应用程序控制实现哪些功能,是在设备底层还需要编写驱动程序,确保可实现USB通信,在生产研发中,驱动程序部分和应用程序部分大多由软件工程师完成,所以USB协议分析仪是硬件工程师和软件工程师都需要的测试设备。

    USB协议分析仪是按照USB协议,将总线上的信号翻译成数据,再将数据逐层解析,分析其传输数据的含义。在这个过程中,可将USB传输过程中的错误明确的指示出来,用户可根据上下文关系找到问题所在。

     

     

     

    分析过程

    在本实验中,如图所示,PC端应用程序的主要功能是:按下ADD键,给DE2发送加1的指令,显示在DE2实验板的液晶显示屏上;按下CLEAR键,给设备发送清零的指令,DE2实验板的液晶显示屏上的显示为00;通过这个简单的应用程序,我们可以了解实验板上USB固件程序,计算机上USB驱动程序是否可以正确工作。

     

    如图所示,在应用程序的源程序中,点击ADD,发送的数据为“AA AB AC AD AE AF A0 A1”,这个就是我们要在USB通信过程中需要传输的数据。传输了这一组数据也就表示传输了ADD指令。

     

    下面,我们用Ex200来捕获发送的ADD指令数据以及其前后过程。分析捕捉到的数据搜索到DATA0DATA1数据包内容皆为“AA AB AC AD AE AF A0 A1”,与源代码一致。如图所示,为DATA0数据包的内容。我们每次按下ADD控件,就可以捕获到这一组数据,这说明USB通信没有问题,可以进行下一步的大数据量传输与通信。

     

     

    又如图所示,在应用程序的源程序中,点击CLEAR,发送的数据为“55 55 5C 5D 5E 5F 50 51”,这个就是我们要在USB通信过程中需要传输的数据。传输了这一组数据也就表示传输了CLEAR指令。:

     

    我们用Ex200来捕获发送的CLEAR指令数据以及其前后过程。分析捕捉到的数据搜索到DATA0DATA1数据包内容皆为“55 55 5C 5D 5E 5F 50 51”,与源代码一致。如图所示,为DATA0数据包的内容。我们每次按下CLEAR控件,就可以捕获到这一组数据。

     

     

    另外,USB协议分析仪是一种很好的学习USB协议的工具,如图所示,通过USB协议分析仪可分析并了解USB设备枚举过程,在教学中可以生动地说明USB通信传输过程,在实际研发中,也可提高效率,缩短开发周期。

     

    小结

    USB协议分析仪是在USB开发过程中必不可少的工具,在研发过程中起到事半功倍的效果,随着USB通信接口的广泛使用,USB协议分析仪也会成为更普及的测试仪器。经过一段时间的发展,USB协议分析仪也趋于成熟,主机体积更加小巧,不需要外加电源即可工作,软件界面更加人性化,让人一目了然。USB协议从1.02.0,再到最新的USB3.0,协议分析仪也会追随USB协议发展的脚步,支持所有版本的测试。

    展开全文
  • USB协议分析仪

    千次阅读 2020-03-21 09:34:58
    USB协议分析仪

    1 ULPI PHY passive sniffing mode
    概念: non driving, no pull-up, no pull-down

    Function Control.opMode = 1; // non-Driving
    OTG Control.DpPulldown = 0; // no pull-down
    OTG Control.DmPulldown = 0; // no pull-down
    USB IO.ChargerPullupEnDP = 0; // no pull-up
    USB IO.ChargerPullupEnDM = 0; // no pull-up

    2 Beagle USB Analyzer
    2.1 Beagle USB 12 Analyzer
    在USB Host和Device之间的DP/DM上连接一个Fairchild USB1T11A,Fairchild USB1T11A连接到隔离器件ADUM1400后,隔离器件再连接到FPGA;FPGA通过CY7C68013A连接到PC。
    Figure 2-1 Beagle USB 12 Analyzer

    2.2 Beagle USB 480 Analyzer
    USB 2.0的协议分析仪有2个PHY,支持LS/FS的Fairchild USB1T11A,支持HS的USB3300(passive sniffing mode)。
    Figure 2-2 Beagle USB 480 Analyzer

    2.3 Beagle USB 5000 v2 analyzer
    有2块PCB,下层是模拟PCB,上层是数字PCB,数字PCB上包括FPGA和CYUSB3014 BZX,其中CYUSB3014 BZX负责上传数据到PC,该芯片在数字PCB上的位置靠近Target Host Port口。

    2.4 URLs
    Review: Total Phase Beagle USB 12 Analyzer
    https://eleccelerator.com/review-total-phase-beagle-usb-12-analyzer/

    Beagle USB 480
    https://www.bunniestudios.com/blog/?p=4106

    3 OpenVizsla
    3.1 FPGA-based USB analyzer
    在USB Host和Device之间的DP/DM上连接一个USB3343(passive sniffing mode),USB3343连接到FPGA;FPGA通过FIFO模式连接到FT2232H,FT2232H连接到PC。
    Figure 3-1 OpenVizsla board

    3.2 URLs
    Open Hardware FPGA-based USB analyzer
    http://openvizsla.org/
    https://github.com/openvizsla

    USB 2.0 Bus/Protocol Analyzer Hardware/Software Comparison
    http://www.summitsoftconsulting.com/UsbAnalyzers.htm

    4 Windows软件抓包工具
    4.1 Bus Hound

    4.2 USBPcap
    USBPcap - USB Packet capture for Windows
    https://desowin.org/usbpcap/

    5 Linux usbmon抓包
    5.1 sniff原理
    binary格式路径:/dev/usbmonX
    text格式路径:/sys/kernel/debug/usb/usbmon

    获得usbmon的主设备号:cat /proc/devices
    创建binary节点:
    mknod /dev/usbmon0 c $major 0
    mknod /dev/usbmon1 c $major 1
    mknod /dev/usbmon2 c $major 2

    5.2 usbmon tcpdump
    1)mount -t debugfs none_debugs /sys/kernel/debug
    2)cat /sys/kernel/debug/usb/devices - 确定usb的总线号
    3)tcpdump -D
    4)tcpdump -i usbmon1 -s 128 -w /data/usb_sniff.pcap &
    5)killall tcpdump
    6)wireshark工具打开usb_sniff.pcap

    usbmon1 - xHCI LS/FS/HS
    usbmon2 - xHCI SS

    5.3 Wireshark过滤规则
    1)usb.src == "1.6.1" and usb.dst == "host" - 改到对应的USB bus_no.addr.ep_no
    2)usb.src == host and ublox

    5.4 USB协议URB解析Wireshark插件
    usb_table = DissectorTable.get("usb.bulk")
    usb_table:add(0xff, my_proto)
    usb_table:add(0xffff, my_proto)

    5.5 usbmon sysfs接口
    cat /sys/kernel/debug/usb/usbmon/1u > /sdcard/1u_usbmon.txt
    命令中1u表示Bus=01,通过命令获得cat /sys/kernel/debug/usb/devices

    cd /sys/kernel/debug/usb/usbmon
    反向查找,查找不包含"1:003:2"(总线号:设备地址:端点号)字符串的其它内容
    cat 1u  |grep -v "1:003:2"
    排除多个字符串:cat 1u  |grep -vE "1:003:2|1:004:1"

    5.6 usbfs
    echo 1 > /sys/module/usbcore/parameters/usbfs_snoop

    6 Abbreviations
    DSLogic:Dream Source Lab

    展开全文
  • saleae逻辑分析仪软件客户资料;包含硬件全部资料。适用于串口数据分析, 尤其在分析 时序,比如 1wire、 I2C、 UART、 SPI、 CAN等数据的时候,应用逻辑分析仪解决问 题非常快速。
  • USB抓包工具属于小众产品,开源的就更少了!! USB抓包工具分为纯软件的和硬件的两种,纯软件usb抓包工具需要在系统能正确枚举usb设备的前提...1.USBlyzer(能很方便的帮你分析出HID报告描述符等等) 2.Bus Hound...

    USB抓包工具属于小众产品,开源的就更少了!!

    USB抓包工具分为纯软件的和硬件的两种,纯软件usb抓包工具需要在系统能正确枚举usb设备的前提下才能让内核的钩子函数捕抓到数据,而后者在usb不正常时也能捕捉到链路数据(令牌包等),属于更底层的抓包方式。

    一、我用过的并且好用的纯软件USB抓包工具有:

    1.USBlyzer(能很方便的帮你分析出HID报告描述符等等)

    下面几幅图简单介绍它的使用方法:

            还有一个常用的USB properties界面,用于观看设备描述符、配置描述符、接口描述符以及端点描述符,对于HID设备,还能看到HID报告描述符,挺好用的:

    2.Bus Hound(没有协议分析,但抓包很直观,而且允许你发送一些自定义的控制传输命令给设备,用于调试(如下图所示)。另外,Bus Hound不单能抓usb总线,包括串口、PCIE等都能抓)

    很遗憾,他们都不是开源的,linux下倒是有开源的,如linux平台下“usbmon驱动+tcpdump”方式抓包。

    3.linux使用usbmon驱动+tcpdump+wirshark调试:

    需要编译linux加入usbmon驱动:
    make  ARCH=arm CROSS_COMPILE=arm-linux-gnueabihf- menuconfig
                       Device Drivers -->
                                USB Support -->
                                         USB Monitor --> Select "M"

    modprobe usbmon
    mount -t debugfs none_debugs /sys/kernel/debug
    cat /sys/kernel/debug/usb/devices

    选择包含有 P: Vendor=xxx ProdID=xxx Rev= xxx 的段落(即筛选出你要抓包的USB设备的PID/VID号)
    如果总线号是1(即Bus=01),则是1u,如果总线号是2,则是2u,依次类推。特殊情况是0u表示监听所有总线
    cat /sys/kernel/debug/usb/usbmon/1u > ./usbmon.txt得到原始数据:

     该原始数据是天书,需要借助linux内核文档“Documentation/usb/usbmon.txt”进行人工分析,下面只是其中一小段:

    或者使用tcpdump -i usbmon1 -w /var/usb_log.pcap将捕捉到的usb数据导入到wirshark3.x上阅读,能做简单的Class协议分析。其中“tcpdump -D”可以列举可以抓包的设备,包括以太网、USB、CAN总线等。

    另外,USB错误码文档在Linux内核源码路径下的Documentation/usb/error-codes.txt有关于usb的错误代码意义说明。

    二、开源硬件usb抓包工具

    1.玩具级别的usb sniffer(硬件平台FTDI+USB PHY+FPGA )

    http://ultra-embedded.com/usb_sniffer/

    对应github代码路径:https://github.com/ultraembedded/usb_sniffer

    FPGA使用verilog开发,主机软件使用C语言开发,功能比较简单,而且过滤条件也简陋,但麻雀虽小五脏俱全,有兴趣可以研究一下,硬件方面,作者使用零散的模块搭建,比较儿戏,我自己也做过实验,但在USB PHY那里跪了,FPGA怎么都抓不到USB3300的数据包,没有去深入分析问题所在。

    ---2020-06-22:作者又出了一个新的usb抓包工具,代码在https://github.com/ultraembedded/usb2sniffer,内部模块充分使用AXI-4作为芯片通信总线,不过很可惜的是,硬件不是他自己设计的,而是使用商业的板子( LambdaConcept USB2Sniffer),我们在国内也很难买到外国的开发板,同时原理图也不公开,我们就没办法制作电路板了。有兴趣可以阅读他的代码,但制作就免了,除非读者自己设计电路,然后修改作者的代码。

    2.OpenVizsla(硬件平台FTDI+USB PHY+FPGA)

    http://openvizsla.org/

    对应github代码路径:https://github.com/openvizsla/ov_ftdi

    也可以到https://download.csdn.net/download/litao31415/12503613下载,该版本精简了一下,更新了migen,删除了misoc

    完全开源,包括pcb电路板打样文件和BOM物料清单都有,FPGA使用python开发,主机软件亦使用python进行开发。个人觉得FPGA使用python开发目前还不成熟(Migen-A Python toolbox for building complex digital hardware),代码看起来比较冗余,我已经在ubuntu虚拟机上编译出ov3.bit了,暂不打算阅读FPGA源码,而是尝试改写其主机软件加入常用class的协议分析功能(但其实我改它用处并不大,因为目前OpenVizsla已经支持很多分析软件了,譬如wireshark、Beagle 480的分析软件等等)。usb PHY使用了ULPI接口,优点是管脚少,缺点是FPGA需要实现一个适配层转换为UTMI+接口。FPGA使用老掉牙的spartan6,开发工具使用ISE14.7,不过还好Xilinx官网说至少会供货到2027年,也胜在封装够简易(TQFP-144),方便手工焊接。4层板打板也便宜,我已经焊接好一套,正在调试中,打算实测一下效果!


    此分割线之间的内容更新于2020-02-06:

           利用疫情期间丰富的春节假期,调试了一下openvizsla板子,虽然年前我手工焊接好一套,但在调试过程中相当于要重新再焊接一次,因为超多虚焊和管脚短路,反复焊接焊到我心灰意冷,尤其USB3343芯片,4mmx4mm QFN-24封装的,热风枪焊接完眼睛都花了。焊接技巧:拿镊子的手不要抖,拖锡(吸锡)要耐心。最后,焊接方面应该没问题了,又发现SDRAM型号兼容性不太好,由AS4C16M16S-7TCN改为MT48LC16M16A2P-75貌似好一点,过年快递不工作,唯有加点钱顺丰发货。最后貌似能抓包了,但运行官方的测试SDRAM命令貌似有点问题(我还没研究怎么去定位,理论上应该要在FPGA上写测试代码,用chipscope抓包分析看是控制时序不行还是虚焊还是其他问题,如果是用verilog写的还好,不过本项目是使用Migen库,没阅读过该库api说明,都不知道怎么例化chipscope来抓信号调试,先放下了,因为换另一批MT48LC16M16A2P-75又好了):

    测试:$sudo ./ovctl.py report
    USB PHY Tests
        ULPI PHY ID: 04240009 (SMSC 334x)
        ULPI Scratch register IO test: OK
        PHY Function Control Reg:  48
        PHY Interface Control Reg: 00
    SDRAM tests
        ... 0: OK
        ... 1: OK
        ... 2: OK
        ... 3: FAIL

    换另一批次的MT48LC16M16A2P-75芯片后测试正常:

    $ sudo ./ovctl.preport
    USB PHY Tests
        ULPI PHY ID: 04240009 (SMSC 334x)
        ULPI Scratch register IO test: OK
        PHY Function Control Reg:  48
        PHY Interface Control Reg: 00
    SDRAM tests
        ... 0: OK
        ... 1: OK
        ... 2: OK
        ... 3: OK
        ... 4: OK
        ... 5: OK
        ... all passed

    1)接上U盘后“$ sudo ./ovctl.py sniff hs | tee usbdump.log”能抓包:
    [        ]  10.379599 d=  0.000000 [ 43.3 + 74.383] [ 34] DATA0: 55 53 42 43 40 28 79 13 00 00 00 00 00 00 06 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 34 3e 
    [        ]  10.379600 d=  0.000001 [ 43.3 + 75.333] [  1] NYET 
    [        ]  10.379627 d=  0.000027 [ 43.3 +102.800] [  3] IN   : 18.1 
    [        ]  10.379628 d=  0.000000 [ 43.3 +103.300] [  1] NAK 
    [        ]  10.379650 d=  0.000022 [ 43.4 +  0.667] [  3] IN   : 18.1 
    [        ]  10.379651 d=  0.000000 [ 43.4 +  1.167] [ 16] DATA0: 55 53 42 53 40 28 79 13 00 00 00 00 00 81 ab 
    [        ]  10.379651 d=  0.000001 [ 43.4 +  1.900] [  1] ACK 
    0 / 16777216 (0.00 % utilization) 411 kB | 0 overflow, 39cdd08a total | R00066fc7 W00066fc7
    [        ]  10.784078 d=  0.404427 [191.7 +106.433] [  3] PING : 18.2 
    [        ]  10.784079 d=  0.000000 [191.7 +106.933] [  1] ACK 
    [        ]  10.784081 d=  0.000002 [191.7 +109.417] [  3] OUT  : 18.2 
    [        ]  10.784081 d=  0.000000 [191.7 +109.750] [ 34] DATA1: 55 53 42 43 10 70 fb 1a 00 00 00 00 00 00 06 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 81 37 
    [        ]  10.784082 d=  0.000001 [191.7 +110.667] [  1] NYET 
    [        ]  10.784112 d=  0.000030 [192.0 + 15.817] [  3] IN   : 18.1 
    [        ]  10.784113 d=  0.000000 [192.0 + 16.317] [  1] NAK 
    [        ]  10.784134 d=  0.000021 [192.0 + 37.400] [  3] IN   : 18.1 
    [        ]  10.784135 d=  0.000000 [192.0 + 37.883] [ 16] DATA1: 55 53 42 53 10 70 fb 1a 00 00 00 00 00 db a3 
    [        ]  10.784135 d=  0.000001 [192.0 + 38.617] [  1] ACK 
    [        ]  10.784249 d=  0.000113 [192.1 + 27.117] [  3] PING : 18.2 
    [        ]  10.784249 d=  0.000000 [192.1 + 27.617] [  1] ACK 
    [        ]  10.784252 d=  0.000002 [192.1 + 30.083] [  3] OUT  : 18.2 

    .................

    但不稳定,有时会出现异常,尤其在U盘传输大文件时:

    ........
    [        ] 396.229368 d=  0.000009 [142.4 + 29.783] [  1] ACK 
    [        ] 396.229369 d=  0.000000 [142.4 + 30.083] [  3] IN   : 12.1 
    [        ] 396.229369 d=  0.000000 [142.4 + 30.583] [  1] NAK 
    [        ] 396.229395 d=  0.000026 [142.4 + 56.383] [  3] IN   : 12.1 
    Unmatched byte ba - discarding
    Exception in thread Thread-1:
    Traceback (most recent call last):
      File "/usr/lib/python3.6/threading.py", line 916, in _bootstrap_inner
        self.run()
      File "/usr/lib/python3.6/threading.py", line 864, in run
        self._target(*self._args, **self._kwargs)
      File "/home/default/work/other/usb_stuff/ov_ftdi/software/host/LibOV.py", line 637, in __comms
        raise self.__comm_exc
      File "/home/default/work/other/usb_stuff/ov_ftdi/software/host/LibOV.py", line 616, in callback
        code = service.presentBytes(self.__buf)
      File "/home/default/work/other/usb_stuff/ov_ftdi/software/host/LibOV.py", line 310, in presentBytes
        self.consume(b[:size])
      File "/home/default/work/other/usb_stuff/ov_ftdi/software/host/LibOV.py", line 558, in consume
        assert ''.join("%02x"% r for r in buf) in ["e0e1e2", "e8e9ea"], buf
    AssertionError: b'\xe0b\xb1'
    需要运行“sudo ./ovctl.py -l”重新加载FPGA程序后,再重新抓包才恢复正常!

    2)另外,出现抓不了包时,有可能需要重新插拔被测设备。

    3)接上USB鼠标,打算抓取低速鼠标数据“sudo ./ovctl.py sniff ls”,发现只能抓取到最开始的枚举数据(setup阶段)就停掉了,手动鼠标,抓取不到X和Y的数据变化,重新加载FPGA重新也无济于事!(后面发现原来此时PC并没有识别出鼠标来,抓不到xy坐标数据也能说得通,但问题是,为什么此时PC会识别不出来鼠标设备呢?拔掉直接接到PC上其实是ok的,即鼠标本身是没问题的,难道是接PC这端的USB线缆太长了!--0207--换笔记本上的USB充电口(黄色,没有测试蓝色的USB3.x),发现只有这个USB口能抓到鼠标数据,用万用表测量openvizsla上的USB端子,无论PC是否用充电口,Vbus均为4.96v,板上两个usb口间各个引脚电阻均为0.5欧左右,符合规范。猜想是D+/D-对地的阻抗不符合USB协议规范,我去掉R4/R5两个电阻,防止FPGA输出杂讯影响D+/D-,但没有改善。)

    4)抓包输出标准文档,供第三方软件协议分析

    目前抓包输出格式仅支持"verbose", "custom", "pcap"和 "iti1480a",如:

    sudo ./ovctl.py -l sniff hs --format pcap --out ./my_upan.pcap供wireshark3.x分析

    如果要限定抓包时间为5s,可以设置timeout参数,如:

    sudo ./ovctl.py -l sniff hs --timeout 5 --format iti1480a --out ./my_upan.iti1480a等

    总结一下:

    1.如果下次有开源硬件感兴趣需要制作,我宁愿花钱请贴片厂焊接算了,手工焊接太折腾人了!

    2.openvizsla抓包需要手工指定ls、fs和hs(即低速、全速和高速)这个不好,不够自动化,搞错了会抓不到数据。

    3.openvizsla终究不是企业产品,没有经过大量验证,有很多兼容性问题,如即使芯片型号一致但批次不同(如SDRAM),时序还是有偏差,导致抓包不稳定。(我怀疑兼容性问题是由于该项目使用python转换为verilog代码的Migen库有关,开发过FPGA的人都知道,逻辑正确并不代表实际硬件能正确运行,自动转换的东西肯定没有手工编写verilog代码的时序优化做得好。综合前仿真过了,实现后也可能出现时序不过关,如产生毛刺,建立保持时间不足等,SDRAM这种运行频率达100MHz甚至133MHz高频的器件,没有做时序仿真真的很容易出问题!)

    openvizsla的调试暂告一段落,初步能抓包分析,但不够稳定,还不能用于稳定调试usb设备!!



    另附Openvizsla运行环境的搭建:

    PC使用ubuntu18.04虚拟机,windows的运行环境还请读者自行研究。

    1),源码安装libusb-1.0.22.tar.bz2
    .configure 
    make
    sudo make install
    2),安装python3.6和pip3
    3),安装crc库: pip3 install crcmod

    在启动sudo ./ovctl.py sniff hs测试时,可能会报错qemu-system-x86_64: symbol lookup error: qemu-system-x86_64: undefined symbol: libusb_set_option?
     这是因为我们安装的libusb在/usr/local/lib/目录下,但是,在此运行过程中是去根目录的`/lib`目录下找对应的库文件,所以会报找不到符号。
     解决办法是:
            sudo ln -sf /usr/local/lib/libusb-1.0.so /lib/x86_64-linux-gnu/libusb-1.0.so.0
    参考https://blog.csdn.net/shenwanjiang111/article/details/82898119

    Openvizsla本身含有发布者早已编译好的fpga固件,但如果读者想自行编译FPGA,则还需在ubuntu下安装spartan6的编译环境,Migen工具库会自动调用ISE进行编译“由python转化的verlog代码”。

    4),安装ISE14.7软件
    https://www.xilinx.com/support/download/index.html/content/xilinx/en/downloadNav/vivado-design-tools/archive-ise.html
    https://www.xilinx.com/member/forms/download/xef.html?filename=Xilinx_ISE_DS_Lin_14.7_1015_1.tar

    发现并不能正常打开ISE软件,参考下面的网址进行修复:
    https://www.xilinx.com/support/answers/58400.html
    https://forums.xilinx.com/t5/Installation-and-Licensing/xilinx-license-configuration-manager-not-working-in-xilinx14-7/td-p/411795
    下载libQt_Network.zip解压后得到libQt_Network_lin64.so,将libQt_Network_lin64.so重命名为libQt_Network.so后mv到/opt/Xilinx/14.7/ISE_DS/common/lib/lin64
    运行/opt/Xilinx/14.7/ISE_DS/common/bin/lin64/xlcm加入lincense,而lincense跟windows用的一样,能从网络上获取到。



    3.PhyWhisperer-USB(硬件平台M3+USB PHY+FPGA)

    https://www.crowdsupply.com/newae/phywhisperer-usb

    对应github代码路径:https://github.com/newaetech/phywhispererusb

    也是完全开源,这个项目比较新,2019年才启动,同样也是4层板。FPGA使用verilog语言开发,主机软件使用python开发。它除了支持普通的usb抓包外,还支持简单的功率分析。usb PHY使用UTMI+接口的USB3500-ABZJ芯片,无需操作寄存器直接对接FPGA。而FPGA使用spartan 7,属于比较新的系列,使用xilinx新一代开发工具vivado进行开发。因为芯片是BGA封装不方便手工焊接,需要花钱让贴片厂焊接,把动手能力差的创客/极客挡在门外,当然有钱人除外。另外板内也不含SDRAM,没法对数据进行缓冲处理,只使用FPGA片内有限的Block RAM(仅360Kbit容量)作为缓冲区,所以当抓USB2.0摄像头这种大量、连续的USB数据时应该存在丢数据的可能,最后,该项目还包含一个microchip的单片机,我认为是一个败笔,虽说可编程器件比较灵活(官网是这么说的),但不应该搞那么多可编程器件,维护那么多份不同类型的代码,容易出bug,使用FTDI的usb转FIFO多好,无需编程,我想该项目应该是micochip公司有份出钱搞的,看PhyWhisperer-USB官网介绍就知道了(PhyWhisperer-USB is part of the Microchip Get Launched 2019 design competition!),肯定尽量用多点micochip的芯片(另外usb PHY也是他家的产品)才能申请到钱,有钱才有动力,作为中国人,你懂的。综上,PhyWhisperer-USB对比先驱OpenVizsla,还没有完全成熟,各位创客/极客们可以先观望一段时间再动手制作,有能力者也可以参与开发,在github上提交push请求,或者修改Altium Designer工程,修改PCB和代码以适应自己的需求,毕竟它是完全开源的,可以任意修改!

            以上3款硬件USB抓包工具均支持硬件级别的条件触发,譬如选择只捕捉某个地址的端点、只看IN+ACK,过滤掉OUT+NAK等等。

            FPGA均使用“从串配置”的配置模式,优点是方便随时升级fpga固件、省掉一个spi nor flash,具体可参考Xilinx官网的UG470等文档。其工作原理是“微控制器MCU/FTDI等芯片利用SPI总线或并行总线将配置文件传到FPGA后加载,MCU先主动拉低PROGRAM_B(CS#)管脚以启动配置,然后轮询FPGA的INIT_B管脚电平,当它为高电平时代表FPGA准备好了,此时MCU提供SPI时钟(CLK)和数据(MOSI)直至FPGA配置完毕,当FPGA的DONE管脚被拉高就代表FPGA加载成功。但如果INIT_B被拉低或DONE一直为低电平则代表配置失败,需重试,如果重试多次均失败就需要排查问题了”,参考电路图如下,其中箭头代表信号的传输方向:

    为了对比几种开源的usb分析仪,盗用PhyWhisperer-USB的图:

            正如我开头所说,USB协议分析仪终究是小众产品,这导致了商业抓包工具非常昂贵,譬如国外的Beagle 480、USB Explorer 200等,国内的,要点名批评沁恒科技的usb2.0分析仪,自己软件做得不好没关系,还不开放API接口让我们二次开发分析软件,也不能输出wireshark能分析的文档格式,不过它硬件做得也还行,也是支持触发源输入的。所以对于我们调试USB设备的朋友来说,拥有一台自己的USB抓包仪真是如虎添翼,上述三款开源的usb抓包工具你值得拥有,感兴趣的同学赶紧去打板、去github下载代码编译吧!

            最后,很感慨我们国内的开发者不如国外的,这里我说的不是技术这一层面,而是指那一份开源精神,那一份热情!

     

    展开全文
  • USB 协议分析(含基本协议和 USB 请求和设备枚举)

    万次阅读 多人点赞 2018-08-30 00:49:29
    目录 1. 物理特性 1.1 引脚 1.2 USB 信号(差分信号) ...2. 通信协议 2.1 包组成(Packets Content) 2.1.1 PID 域 2.1.2 Address 地址域 2.1.3 Frame Number 帧号域 2.1.4 Data 数据域 2.1.5 C...

    目录

    1. 物理特性

    1.1 引脚

    1.2 USB 信号(差分信号)

    1.3 USB 信号编码(NRZI)

    1.4 USB 字节序

    1.5 USB 设备检测

    2. 通信协议

    2.1 包组成(Packets Content)

    2.1.1 PID 域

    2.1.2 Address 地址域

    2.1.3 Frame Number 帧号域

    2.1.4 Data 数据域

    2.1.5 CRC域

    2.2 包类型(Packets Type)

    2.2.1 令牌包(Token)

    2.2.2 数据包(Data)

    2.2.3 握手包(Handshake)

    2.3 事务(Transaction)

    2.3.1  SetUp 事务

    2.3.2  IN 事务

    2.3.3  OUT 事务

    2.4 传输(Transfer)

    2.4.1 控制传输 (Control Transfer)

    2.4.2 批量传输 (Bulk Transfer)

    2.4.3 中断传输 (Interrupt Transfer)

    2.4.4 同步传输 (Isochronous)

    3. USB 请求(用于控制传输)

    4. USB 描述符

    4.1 设备描述符

    4.2 配置描述符

    4.3 接口描述符

    4.4 端点描述符

    4.5 字符串描述符

    5 USB 枚举

    5.1 获取设备描述符 GET_DESCRIPTOR

    5.2 设置地址SET_ADDRESS

    5.3 请求设备描述 GET_DESCRIPTOR

    5.4 请求配置描述 GET_DESCRIPTOR

    5.5 读取完整设备描述及配置描述

    5.6 配置设备 SET_CONFIGURATION


    1. 物理特性

    1.1 引脚

    一条USB传输线分别由地线、电源线、D+和D-四条线构成,D+和D-是差分输入线,它使用的是3.3V的电压(与CMOS的5V电平不同),而电源线和地线可向设备提供5V电压,最大电流为500mA(可以在编程中设置)。

    引脚标号信号名称缆线颜色
    1Vcc
    2Data- (D-)
    3Data+ (D+)绿
    4GND


            USB设备可以直接和HOST通信,或者通过Hub和Host通信。一个USB系统中仅有一个USB 主机,设备包括USB功能设备和USB HUB,最多支持127个设备。物理连接指的是USB传输线。在USB 2.0系统中要求使用屏蔽双绞线。

    1.2 USB 信号(差分信号)

    使用差分信号进行数据传输,有效的降低外接带来的干扰。

    1.3 USB 信号编码(NRZI)

    USB 数据传输的传输使用反向不归零编码进行传送(NRZI)

    反向不归零编码方式可以保证数据的完整性,而且不要求传输过程中由独立的时钟信号。

    1.4 USB 字节序

    LSB 先发,MSB 后

    1.5 USB 设备检测

    USB1.0和USB1.1支持1.5Mb/s的低速模式和12Mb/bs的全速模式。在USB2.0以上支持480Mb/s的高速模式。

    当 USB 设备接入系统时刻,系统通过检测 USB 上的 D+或者D- 线上的上拉电阻的方式来识别低速全速设备。如下图所示,当主机端没有设备接入的时候,其D+和D-的下拉电阻使得其电压几乎为 0V;当全速/低速设备接入后,在D+或者D-端的上拉电阻会使得D+/D-出现高电平,而另外一根是低电平。主机端便知道有设备插入。

    对于高速设备,和全速设备一样,在D+上存在上拉电阻,对于高速设备的的识别,主机先把高速设备检测为全速设备,然后再通过“Chirp 序列”的总线握手机制来识别高速和全速设备。

    2. 通信协议

    USB 协议中:

    域组成了包,不同的域,组成了不同类型的包(Token、Data、HandShake)。

    多个包一起组成了一个事务(SetUp事务,IN 事务,OUT 事务)

    多个事务,进而组成了不同类型的传输(控制传输,中断传输,批量传输,同步传输)

    2.1 包组成(Packets Content)

    包(Packet)是USB系统中信息传输的基本单元,所有数据都是经过打包后在总线上传输的。数据在 USB总线上的传输以包为单位,包只能在帧内传输。高速USB总线的帧周期为125us,全速以及低速 USB 总线的帧周期为 1ms。帧的起始由一个特定的包(SOF 包)表示,帧尾为 EOF。EOF不是一个包,而是一种电平状态,EOF期间不允许有数据传输。 
    包是USB总线上数据传输的最小单位,不能被打断或干扰,否则会引发错误。若干个数据包组成一次事务传输,一次事务传输也不能打断,属于一次事务传输的几个包必须连续,不能跨帧完成。一次传输由一次到多次事务传输构成,可以跨帧完成。

    USB包由五部分组成,即同步字段(SYNC)、包标识符字段(PID)、数据字段、循环冗余校验字段(CRC)和包结尾字段(EOP),包的基本格式如下图:

    2.1.1 PID 域

    不同的 PID 标识了不同类型的 USB 包。由四位标识符 + 四位标识符反码构成

    这里只用(PID0~4),PID4~7是PID0~4的取反,用来校验 PID

    根据 USB2.0 的 Spec 描述:

    可以看出,由 PID 主要将 USB 的包分为了 4 类:

    1. 令牌包(Token) :

            0x01:输出(OUT)启动一个方向为主机到设备的传输,并包含了设备地址和标号。

            0x09:输入(IN) 启动一个方向为设备到主机的传输,并包含了设备地址和标号。

            0x05:帧起始(SOF)表示一个帧的开始,并且包含了相应的帧号。

            0x0d:设置(SETUP)启动一个控制传输,用于主机对设备的初始化。

    2. 数据包(Data) :

            0x03:偶数据包(DATA0)。

            0x0b:奇数据包(DATA1)。

            0x07:高速设备的 PID 的同步包

            0x0f :高速设备分离包,高带宽的同步事务

    3. 握手包(HandShake):

            0x02:确认接收到无误的数据包(ACK)。

            0x0a:无效(NAK),接收(发送)端正在忙而无法接收(发送)信息。

            0x0e:错误(STALL),端点被禁止或不支持控制管道请求。

            0x06:无响应(NYET)。

    4. 特殊类

            前导包,错误包,分裂事务和 PING 测试

    PID            数据传输方向

    IN              Device->Host

    OUT         Host->Device

    SETUP    Host->Device

    PING        Device->Host

    2.1.2 Address 地址域

    地址域有两部分组成:

    【 7bits 的设备地址 ADDR + 4 bits 的端点地址 ENDP】

    可以知道,USB 系统最大支持链接 127 个设备,每个设备最多 2^4=16 个端点。

    这个 ENDP 只用在 IN/OUT/SETUP令牌包中。

    2.1.3 Frame Number 帧号域

    当USB令牌包的 PID 为 SOF时候,其数据字段必须为11位的帧序列号

    帧号占11位,主机每发出一个帧,帧号都会自加1,当帧号达到0x7FF时,将归零重新开始计数。对于同步传输有重要意义。

    2.1.4 Data 数据域

    仅存在于 DATA 信息包,根据不同的传输类型,拥有不同大小的字节(0--1023字节)

    2.1.5 CRC域

    用于进行数据的 CRC 校验

    2.2 包类型(Packets Type)

    2.2.1 令牌包(Token)

    根据域的 PID 描述,令牌包有4种:

    令牌包有四种:

    • OUT: 通知设备将要输出一个数据包
    • IN: 通知设备返回一个数据包
    • SETUP: 只用在控制传输中,也是通知设备将要输出一个数据包,与OUT令牌的区别是:只使用DATA0数据包,且只能发到device的控制端点
    • SOF: 在每帧开始时以广播的形式发送,针对USB全速设备,主机每1ms/125us产生一个帧,USB主机会对当前帧号进行统计,每次帧开始时通过SOF包发送帧号。

    输入包(IN)、输出包(OUT)和设置包(SETUP)的格式都是一样的:

    SYNC + PID + ADDR(7 bits) + ENDP(4bits) + CRC5(五位的校验码)

    帧起始包(SOF)的格式:

    SYNC + PID + 11位FRAM + CRC5(五位的校验码)

    SOF包由Host发送给Device

    对于full-speed总线,每隔1.00 ms ±0.0005 ms发送一次;

    对于high-speed总线,每隔125 μs ±0.0625 μs发送一次;

    2.2.2 数据包(Data)

    分为DATA0包和DATA1包,当USB发送数据的时候,如果一次发送的数据长度大于相应端点的容量时,就需要把数据包分为好几个包,分批发送,DATA0包和DATA1包交替发送,即如果第一个数据包是DATA0,那第二个数据包就是DATA1。但也有例外情况,在同步传输中(四类传输类型中之一),所有的数据包都是为DATA0,格式如下:

    SYNC + PID + 0~1023字节 + CRC16

    2.2.3 握手包(Handshake)

    结构最为简单的包,格式如下:

    SYNC + PID

    • ACK: 传输正确完成
    • NAK: 设备暂时没有准备好接收数据,或没有准备好发送数据
    • STALL: 设备不能用于传输
    • NYET/ERR: 仅用于高速传输,设备没有准备好或出错

    2.3 事务(Transaction)

    在USB上数据信息的一次接收或发送的处理过程称为事务处理(Transaction)。一个事务由一系统packet组成,具体由哪些packet组成,它取决于具体的事务。

    USB 事务分为3类:

    事务描述
    SetUp 事务主机用来向设备发送控制命令
    Data IN 事务主机用来从设备读取数据
    Data OUT 事务主机用来向设备发送数据

    2.3.1  SetUp 事务

    •【正常】的设置事务处理

    •【设备忙时】的设置事务处理

    •【设备出错】的设置事务处理

    2.3.2  IN 事务

    输入事务处理:表示USB主机从总线上的某个USB设备接收一个数据包的过程。

    •【正常】的输入事务处理

    •【设备忙】时的输入事务处理  

    •【设备出错】时的输入事务处理

    2.3.3  OUT 事务

    输出事务处理:表示USB主机把一个数据包输出到总线上的某个USB设备的过程。

    •【正常】的输出事务处理

    •【设备忙时】的输出事务处理

    •【设备出错】的输出事务处理

    2.4 传输(Transfer)

    在USB的传输中,定义了4种传输类型:

           • 控制传输 (Control Transfer)

           • 中断传输 (Interrupt Transfer)

           • 批量传输 (Bulk Transfer)

           • 同步传输 (Isochronous)

    2.4.1 控制传输 (Control Transfer)

    控制传输由2~3个阶段组成:

          1) 建立阶段(Setup)

          2) 数据阶段(无数据控制没有此阶段)(DATA)

          3) 状态阶段(Status)

          每个阶段都由一次或多次(数据阶段)事务传输组成(Transaction)。

          控制数据由USB系统软件用于配置设备(在枚举时),其它的驱动软件可以选择使用control transfer实现具体的功能,数据传输是不可丢失的。

    1) 建立阶段(Setup)

    主机从USB设备获取配置信息,并设置设备的配置值。建立阶段的数据交换包含了SETUP令牌封包、紧随其后的DATA0数据封包以及ACK握手封包。它的作用是执行一个设置(概念含糊)的数据交换,并定义此控制传输的内容(即:在Data Stage中IN或OUT的data包个数,及发送方向,在Setup Stage已经被设定)。

    2) 数据阶段(DATA)

    数据传输阶段:用来传输主机与设备之间的数据。根据数据阶段的数据传输的方向,控制传输又可分为3种类型:

         A) 控制读取(读取USB描述符)

         B) 控制写入(配置USB设备)

         C) 无数据控制

         A) 控制读取

    是将数据从设备读到主机上,读取的数据USB设备描述符。该过程如下图的【Control Read】所示。对每一个数据信息包而言,首先,主机会发送一个IN令牌信息包,表示要读数据进来。然后,设备将数据通过DATA1/DATA0数据信息包回传给主机。最后,主机将以下列的方式加以响应:当数据已经正确接收时,主机送出ACK令牌信息包;当主机正在忙碌时,发出NAK握手信息包;当发生了错误时,主机发出STALL握手信息包。

         B) 控制写入

    是将数据从主机传到设备上,所传的数据即为对USB设备的配置信息,该过程如下的图【Control Wirte】所示。对每一个数据信息包而言,主机将会送出一个OUT令牌信息包,表示数据要送出去。紧接着,主机将数据通过DATA1/DATA0数据信息包传递至设备。最后,设备将以下列方式加以响应:当数据已经正确接收时,设备送出ACK令牌信息包;当设备正在忙碌时,设备发出NAK握手信息包;当发生了错误时,设备发出STALL握手信息包。

    3) 状态阶段(Status)

    状态阶段:用来表示整个传输的过程已完全结束。
    状态阶段传输的方向必须与数据阶段的方向相反,即原来是IN令牌封包,这个阶段应为OUT令牌封包;反之,原来是OUT令牌封包,这个阶段应为IN令牌封包。

    对于【控制读取】而言,主机开始会一直发送 IN 事务,最后末尾送出 OUT 事务来宣告此次 IN 事务结束;在这个最后的 OUT 事务中,包含完成状态阶段的0长度的DATA1封包。而此时,设备也会做出相对应的动作,送ACK握手封包、NAK握手封包或STALL握手封包。

    相对地对于【控制写入】传输,主机开始会一直发送 OUT 事务,最后末尾送出 IN 事务来宣告此次 OUT 事务结束;在这个最后的 IN 事务中,包含完成状态阶段的0长度的DATA1封包,主机再做出相对应的动作:送ACK握手封包、NAK握手封包或STALL握手封包。

    2.4.2 批量传输 (Bulk Transfer)

    用于传输大量数据,要求传输不能出错,但对时间没有要求,适用于打印机、存储设备等。

    批量传输是可靠的传输,需要握手包来表明传输的结果。若数据量比较大,将采用多次批量事务传输来完成全部数据的传输,传输过程中数据包的PID 按照 DATA0-DATA1-DATA0-…的方式翻转,以保证发送端和接收端的同步。

    一次批量传输(Transfer)由 1 次到多次批量事务传输(Transaction)组成。

    USB 允许连续 3次以下的传输错误,会重试该传输,若成功则将错误次数计数器清零,否则累加该计数器。超过三次后,HOST 认为该端点功能错误(STALL),放弃该端点的传输任务。(重传机制)

    翻转同步:发送端按照 DATA0-DATA1-DATA0-…的顺序发送数据包,只有成功的事务传输才会导致 PID 翻转,也就是说发送端只有在接收到 ACK 后才会翻转 PID,发送下一个数据包,否则会重试本次事务传输。同样,若在接收端发现接收到到的数据包不是按照此顺序翻转的,比如连续收到两个 DATA0,那么接收端认为第二个 DATA0 是前一个 DATA0 的重传。(重传机制)

    它通过在硬件级执行“错误检测”和“重传”来确保host与device之间“准确无误”地传输数据,即可靠传输。它由三种包组成(即IN事务或OUT事务):

            1) token

            2) data

            3) handshake

    For IN Token (即:IN Transaction)

         • ACK: 表示host正确无误地接收到数据

         • NAK: 指示设备暂时不能返回或接收数据  (如:设备忙)

         • STALL:指示设备永远停止,需要host软件的干预 (如:设备出错) 

    For OUT Token (即:OUT Transaction)

         如果接收到的数据包有误,如:CRC错误,Device不发送任何handshake包

         • ACK: Device已经正确无误地接收到数据包,且通知Host可以按顺序发送下一个数据包

         • NAK: Device 已经正确无误地接收到数据包,且通知Host重传数据,由于Device临时状况(如buffer满)

         • STALL: 指示Device endpoint已经停止,且通知Host不再重传

    Bulk读写序列:

     即由一系统IN事务或OUT事务组成。

    2.4.3 中断传输 (Interrupt Transfer)

    中断传输由IN或OUT事务组成。 

    中断传输在流程上除不支持PING 之外,其他的跟批量传输是一样的。他们之间的区别也仅在于事务传输发生的端点不一样、支持的最大包长度不一样、优先级不一样等这样一些对用户来说透明的东西。主机在排定中断传输任务时,会根据对应中断端点描述符中指定的查询间隔发起中断传输。中断传输有较高的优先级,仅次于同步传输。
    同样中断传输也采用PID翻转的机制来保证收发端数据同步。下图为中断传输的流程图。

    中断传输方式总是用于对设备的查询,以确定是否有数据需要传输。因此中断传输的方向总是从USB设备到主机。

    DATA0或DATA1中的包含的是中断信息,而不是中断数据。

    2.4.4 同步传输 (Isochronous)

    它由两种包组成:

            1) token

            2) data

    同步传输不支持“handshake”和“重传能力”,所以它是不可靠传输。

    同步传输是不可靠的传输,所以它没有握手包,也不支持PID翻转。主机在排定事务传输时,同步传输有最高的优先级。同步传输适用于必须以固定速率抵达或在指定时刻抵达,可以容忍偶尔错误的数据上。实时传输一般用于麦克风、喇叭、UVC Camera等设备。实时传输只需令牌与数据两个信息包阶段,没有握手包,故数据传错时不会重传。

    3. USB 请求(用于控制传输)

    标准的USB设备请求命令是用在控制传输中的“初始设置步骤”里的数据包阶段(即DATA0,由8个字节构成)

    也就是说,是控制传输的建立阶段(SetUP)的 DATA0 的 8 个字节。

    命令共有11个,大小都是8个字节,具有相同的结构,由5个字段构成(字段是标准请求命令的数据部分),结构如下(括号中的数字表示字节数,首字母bm,b,w分别表示位图、字节,双字节):

    bmRequestType(1) + bRequest(1) + wvalue(2) + wIndex(2) + wLength(2)

    1USB命令的结构

    偏移量

     长度(字节)

    描述

    0

    bmRequestType

    1

    位图

    请求特征:
    D7:第二阶段数据传输方向 
    0 = 
    主机至设备 
    1 = 
    设备至主机 


    D6D5:种类 
    0=
    标准 
    1=
     
    2=
    厂商 
    3=
    保留 


    D4D3D2D1D0:接受者 
    0=
    设备 
    1=
    接口 
    2=
    端点 
    3=
    其他 


    4..31 保留

    1

    bRequest

    1

    命令类型编码值(见表2

    2

    wValue

    2

    根据不同的命令,含义也不同

    4

    wIndex

    2

    索引或偏移

    根据不同的命令,含义也不同,主要用于传送索引或偏 移

    6

    wLength

    2

     

    如有数据传送阶段,此为数据字节数。

    其中 bRequest 为命令编码值,含意见表2:

    2USB标准命令的编码值

    bRequest

    Value

    GET_STATUS

    0

    CLEAR_FEATURE

    1

    为将来保留

    2

    SET_FEATURE

    3

    为将来保留

    4

    SET_ADDRESS

    5

    GET_DESCRIPTOR

    6

    SET_DESCRIPTOR

    7

    GET_CONFIGURATION

    8

    SET_CONFIGURATION

    9

    GET_INTERFACE

    10

    SET_INTERFACE

    11

    SYNCH_FRAME

    12

    对应的11种的命令,其他的域的含义对照表为:

    3USB11种标准命令

    命令

    bmRequestType

    bRequest

    wValue

    wIndex

    wLength

    Data

    Clear_Feature

    00000000B
    00000001B
    00000010B

    CLEAR_FEATURE

    特性选择符

     
    接口号 
    端点号

    Get_Configuration

    10000000B

    GET_CONFIGURATION

    配置值

    Get_Descriptor

    10000000B

    GET_DESCRIPTOR

    描述表种类(高字节,见表5)和索引(低字节)

    零或语言标志

    描述表长

    描述表

    Get_Interface

    10000001B

    GET_INTERFACE

    接口号

    可选设置

    Get_Status

    10000000B
    10000001B
    10000010B

    GET_STATUS

    零(返回设备状态)
    接口号(对像时接口时)
    端点号(对象是端点时)

    设备,
    接口 , 
    端点状态

    Set_Address

    00000000B

    SET_ADDRESS

    设备地址

    Set_Configuration

    00000000B

    SET_CONFIGURATION

    配置值(高字节为0,低字节表示要设置的配置值)

    Set_Descriptor

    00000000B

    SET_DESCRIPTOR

    描述表种类(高字节,见表5)和索引(低字节)

    零或语言标志

    描述表长

    描述表

    Set_Feature

    00000000B
    00000001B
    00000010B

    SET_FEATURE

    特性选择符(1表示设备,0表示端点)

     
    接口号 
    端点号

    Set_Interface

    00000001B

    SET_INTERFACE

    可选设置

    接口号

    Synch_Frame

    100000010B

    SYNCH_FRAME

    端点号

    帧号

    4. USB 描述符

    USB协议为USB设备定义了一套描述设备功能和属性的有固定结构的描述符,包括标准的描述符即设备描述符、配置描述符、接口描述符、端点描述符和字符串描述符,还有百标准描述符,如类描述符。USB设备通过这些描述符向USB主机汇报设备的各种各样属性,主机通过对这些描述符的访问对设备进行类型识别、配置并为其提供相应的客户端驱动程序。

    USB设备通过描述符反映自己的设备特性。USB描述符是由特定格式排列的一组数据结构组成。

    在USB设备枚举过程中,主机端的协义软件需要解析从USB设备读取的所有描述符信息。在USB主向设备发送读取描述符的请求后,USB设备将所有的描述符以连续的数据流方式传输给USB主机。主机从第一个读到的字符开始,根据双方规定好的数据格式,顺序地解析读到的数据流。

    在USB1.X中,规定了5种标准描述符:

    • 设备描述符(Device Descriptor)
    • 配置描述符(Configuration Descriptor)
    • 接口描述符(Interface Descriptor)
    • 端点描述符(Endpoint Descriptor)
    • 字符串描述符(String Descriptor)

    每个USB设备只有一个设备描述符,而一个设备中可包含一个或多个配置描述符,即USB设备可以有多种配置。设备的每一个配置中又可以包含一个或多个接口描述符,即USB设备可以支持多种功能(接口),接口的特性通过描述符提供

    在USB主机访问USB设备的描述符时,USB设备依照设备描述符、配置描述符、接口描述符、端点描述符、字符串描述符顺序将所有描述符传给主机。一设备至少要包含设备描述符、配置描述符和接口描述符,如果USB设备没有端点描述符,则它仅仅用默认管道与主机进行数据传输。

    4.1 设备描述符

    设备描述符给出了USB设备的一般信息,包括对设备及在设备配置中起全程作用的信息,包括制造商标识号ID、产品序列号、所属设备类号、默认端点的最大包长度和配置描述符的个数等。一个USB设备必须有且仅有一个设备描述符。设备描述符是设备连接到总线上时USB主机所读取的第一个描述符,它包含了14个字段,结构如下:

    4USB设备描述符的结构

    偏移量

    大小

    描述

    0

    bLength

    1

    数字

    此描述表的字节数

    1

    bDecriptorType

    1

    常量

    描述符的类型(此处应为0x01,即设备描述符)

    2

    bcdUSB

    2

    BCD

    此设备与描述表兼容的USB设备说明版本号(BCD 码)

    4

    bDeviceClass

    1

    设备类码:
    如果此域的值为0则一个设置下每个接口指出它自己的类,各个接口各自独立工作。 
    如果此域的值处于1~FEH之间,则设备在不同的接口上支持不同的类。并这些接口可能不能独立工作。此值指出了这些接口集体的类定义。 
    如果此域设为FFH,则此设备的类由厂商定义。

    5

    bDeviceSubClass

    1

    子类

    子类挖码 
    这些码值的具体含义根据bDeviceClass 域来看。 
    bDeviceClass 域为零,此域也须为零 
    bDeviceClass 域为FFH,此域的所有值保留。

    6

    bDevicePortocol

    1

    协议

    协议码 
    这些码的值视bDeviceClass  bDeviceSubClass 的值而定。 
    如果设备支持设备类相关的协议,此码标志了设备类的值。如果此域的值为零,则此设备不支持设备类相关的协议,然而,可能它的接口支持设备类相关的协议。如果此域的值为FFH,此设备使用厂商定义的协议。

    7

    bMaxPacketSize0

    1

    数字

    端点0的最大包大小(仅8,16,32,64
    为合法值)

    8

    idVendor

    2

    ID

    厂商标志(由USB-IF组织赋值)

    10

    idProduct

    2

    ID

    产品标志(由厂商赋值)

    12

    bcdDevice

    2

    BCD 

    设备发行号(BCD 码)

    14

    iManufacturer

    1

    索引

    描述厂商信息的字符串描述符的索引值。

    15

    iProduct

    1

    索引

    描述产品信息的字串描述符的索引值。

    16

    iSerialNumber

    1

    索引

    描述设备序列号信息的字串描述符的索引值。

    17

    bNumConfigurations

    1

    数字

    可能的配置描述符数目

    其中 bDescriptorType 为描述符的类型,其含义可查下表(此表也适用于标准命令Get_Descriptor中wValue域高字节的取值含义):

    5USB描述符的类型值

    类型

    描述符

    描述符值

    标准描述符

    设备描述符(Device Descriptor)

    0x01

    配置描述符(Configuration Descriptor

    0x02

    字符串描述符(String Descriptor

    0x03

    接口描述符(Interface Descriptor

    0x04

    端点描述符(EndPont Descriptor

    0x05

    类描述符

    集线器类描述符(Hub Descriptor

    0x29

    人机接口类描述符(HID

    0x21

    厂商定义的描述符

     

    0xFF

    设备类代码bDeviceClass可查下表:

    6、设备的类别(bDeviceClass

    值(十进制)

    值(十六进制)

    说明

    0

    0x00

    接口描述符中提供类的值

    2

    0x02

    通信类

    9

    0x09

    集线器类

    220

    0xDC

    用于诊断用途的设备类

    224

    0xE0

    无线通信设备类

    255

    0xFF

    厂商定义的设备类

    下表列出了一个USB鼠标的设备描述符的例子,供大家分析一下:

     7、一种鼠标的设备描述符示例 

    字段

    描述符值(十六制)

    bLength

    0x12

    bDecriptorType

    0x01

    bcdUSB

    x0110

    bDeviceClass

    0x00

    bDeviceSubClass

    0x00

    bDevicePortocol

    0x00

    bMaxPacketSize0

    0x08

    idVendor

    0x045E(Microsoft Corporation

    idProduct

    0x0047

    bcdDevice

    0x300

    iManufacturer

    0x01

    iProduct

    0x03

    iSerialNumber

    0x00

    bNumConfigurations

    0x01

    4.2 配置描述符

    配置描述符中包括了描述符的长度(属于此描述符的所有接口描述符和端点描述符的长度的和)、供电方式(自供电/总线供电)、最大耗电量等。主果主机发出USB标准命令Get_Descriptor要求得到设备的某个配置描述符,那么除了此配置描述符以外,此配置包含的所有接口描述符与端点描述符都将提供给USB主机。

    8USB配置描述符的结构

       偏移量

         

     大小

       

       描述

          0

    bLength

    1

       数字

    此描述表的字节数长度。

          1

    bDescriptorType

    1

       常量

    配置描述表类型(此处为0x02

          2

    wTotalLength

    2

       数字

    此配置信息的总长(包括配置,接口,端点和设备类及厂商定义的描述符)

          4

    bNumInterfaces

    1

       数字

    此配置所支持的接口个数

          5

    bCongfigurationValue

    1

       数字

    SetConfiguration()请求中用作参数来选定此配置。

          6

    iConfiguration

    1

       索引

    描述此配置的字串描述表索引

          7

    bmAttributes

    1

       位图

    配置特性: 
    D7
     保留(设为一) 
    D6
     自给电源 
    D5
     远程唤醒 
    D4..0
    :保留(设为一) 
    一个既用总线电源又有自给电源的设备会在MaxPower域指出需要从总线取的电量。并设置D6为一。运行时期的实际电源模式可由GetStatus(DEVICE) 请求得到。

          8

    MaxPower

    1

        mA

    在此配置下的总线电源耗费量。以 2mA 为一个单位。

    下面是一种硬盘的配置描述符示例:

     9、一种硬盘的配置描述符示例 

    字段

    描述符值(十六进制)

    bLength

    0x09

    bDescriptorType

    0x02

    wTotalLength

    0x01F

    bNumInterfaces

    0x01

    bCongfigurationValue

    0x01

    iConfiguration

    0x00

    bmAttributes

    0x0C

    MaxPower

    0x32

    4.3 接口描述符

    配置描述符中包含了一个或多个接口描述符,这里的“接口”并不是指物理存在的接口,在这里把它称之为“功能”更易理解些,例如一个设备既有录音的功能又有扬声器的功能,则这个设备至少就有两个“接口”。

    如果一个配置描述符不止支持一个接口描述符,并且每个接口描述符都有一个或多个端点描述符,那么在响应USB主机的配置描述符命令时,USB设备的端点描述符总是紧跟着相关的接口描述符后面,作为配置描述符的一部分被返回。接口描述符不可直接用 Set_Descriptor 和 Get_Descriptor 来存取。

    如果一个接口仅使用端点0,则接口描述符以后就不再返回端点描述符,并且此接口表现的是一个控制接口的特性,它使用与端点0相关联的默认管道进行数据传输。在这种情况下 bNumberEndpoints 域应被设置成0。接口描述符在说明端点个数并不把端点0计算在内。

    10USB接口描述符的结构

    偏移量

    大小

    说明

           0

    bLength

    1

    数字

    此表的字节数

           1

    bDescriptorType

    1

    常量

    接口描述表类(此处应为0x04

           2

    bInterfaceNumber

    1

    数字

    接口号,当前配置支持的接口数组索引(从零开始)。

           3

    bAlternateSetting

    1

    数字

    可选设置的索引值。

           4

    bNumEndpoints

    1

    数字

    此接口用的端点数量,如果是零则说明此接口只用缺省控制管道。

           5

    bInterfaceClass

            1

    接口所属的类值: 
    零值为将来的标准保留。 
    如果此域的值设为FFH,则此接口类由厂商说明。 
    所有其它的值由USB 说明保留。

           6

    bInterfaceSubClass

            1

    子类

    子类码 
    这些值的定义视bInterfaceClass域而定。 
    如果bInterfaceClass域的值为零则此域的值必须为零。 
    bInterfaceClass
    域不为FFH则所有值由USB 所保留。

           7

    bInterfaceProtocol

            1

    协议

    协议码:bInterfaceClass bInterfaceSubClass 域的值而定.如果一个接口支持设备类相关的请求此域的值指出了设备类说明中所定义的协议.

           8

    iInterface

            1

    索引

    描述此接口的字串描述表的索引值。

    对于 bInterfaceClass 字段,表示接口所属的类别,USB协议根据功能将不同的接口划分成不的类,其具体含义如下表所示:

    11USB协议定义的接口类别(bInterfaceClass

    值(十六进制)

    类别

    0x01

    音频类

    0x02

    CDC控制类

    0x03

    人机接口类(HID

    0x05

    物理类

    0x06

    图像类

    0x07

    打印机类

    0x08

    大数据存储类

    0x09

    集线器类

    0x0A

    CDC数据类

    0x0B

    智能卡类

    0x0D

    安全类

    0xDC

    诊断设备类

    0xE0

    无线控制器类

    0xFE

    特定应用类(包括红外的桥接器等)

    0xFF

    厂商定义的设备

    4.4 端点描述符

    端点是设备与主机之间进行数据传输的逻辑接口,除配置使用的端点0(控制端点,一般一个设备只有一个控制端点)为双向端口外,其它均为单向。端点描述符描述了数据的传输类型、传输方向、数据包大小和端点号(也可称为端点地址)等。

    除了描述符中描述的端点外,每个设备必须要有一个默认的控制型端点,地址为0,它的数据传输为双向,而且没有专门的描述符,只是在设备描述符中定义了它的最大包长度。主机通过此端点向设备发送命令,获得设备的各种描述符的信息,并通过它来配置设备。

    12USB端点描述符的结构

    偏移量

    大小

    说明

    0

    bLength

    1

    数字

    此描述表的字节数长度

    1

    bDescriptorType

    1

    常量

    端点描述表类(此处应为0x05

    2

    bEndpointAddress

    1

    端点

    此描述表所描述的端点的地址、方向: 
    Bit 3..0 : 
    端点号.
    Bit 6..4 : 
    保留,为零 
    Bit 7:    
    方向,如果控制端点则略。 
    0
    :输出端点(主机到设备) 
    1
    :输入端点(设备到主机)

    3

    bmAttributes

    1

    位图

    此域的值描述的是在bConfigurationValue域所指的配置下端点的特性。 
    Bit 1..0 :
    传送类型 
    00=
    控制传送 
    01=
    同步传送 
    10=
    批传送 
    11=
    中断传送 
    所有其它的位都保留。

    4

    wMaxPacketSize

    2

    数字

    当前配置下此端点能够接收或发送的最大数据包的大小。 
    对于实进传输,此值用于为每帧的数据净负荷预留时间。在实际运行时,管道可能不完全需要预留的带宽,实际带宽可由设备通过一种非USB定义的机制汇报给主机。对于中断传输,批量传输和控制传输,端点可能发送比之短的数据包
     

    6

    bInterval

    1

    数字

    周期数据传输端点的时间间隙。 
    此域的值对于批传送的端点及控制传送的端点无意义。对于同步传送的端点此域必需为1,表示周期为1ms。对于中断传送的端点此域值的范围为1ms255ms

    下表是一种鼠标的端点描述符的示例,该端点是一个中断端点:

     13、一种鼠标的端点描述符示例 

    值(十六进制)

    bLength

    0x07

    bDescriptorType

    0x05

    bEndpointAddress

    0x81

    bmAttributes

    0x03

    wMaxPacketSize

    0x04

    bInterval

    0x0A

    4.5 字符串描述符

    字符串描述符是一种可选的USB标准描述符,描述了如制商、设备名称或序列号等信息。如果一个设备无字符串描述符,则其它描述符中与字符串有关的索引值都必须为0。字符串使用的是Unicode编码

    这里具体说一下,还记得之前的设备描述符吗?里面有3个成员:

    iManufacturer

    1

    索引

    描述厂商信息的字符串描述符的索引值。

    iProduct

    1

    索引

    描述产品信息的字串描述符的索引值。

    iSerialNumber

    1

    索引

    描述设备序列号信息的字串描述符的索引值。

    当获得设备描述符后,这3个成员的值,就代表了字符串描述的 Index,如果这个索引为0,则代表这个 USB 设备没有对应的这个项的字符串描述符;

    比如,获得设备描述符后,iManufacturer = 0x00,iProduct = 0x02,iSerialNumber=0x00,说明这个设备没有 Manufacturer 和 SerialNumber 的字符串描述符,只有 Product 的字符串描述符,并且这个 Product 的字符串描述符的 Index是 0x02;马上我们来看这个 Index 有啥用;

    主机请示得到某个字符串描述符时一般分成两步:

    1、首先主机向设备发出USB标准命令Get_Descriptor,其中所使用的字符串的索引值为0

    这个 USB 的 GET_DESCRIPTOR 请求的字段填充方式如下:

    bmRequestType = 0x80 (standard request -- Device Receive -- Device To Host Data)

    bRequest = 0x06 (GET_DESCRIPTOR)

    wValue = (0x03< 8) | 0x00 // ((GET_DESCRIPTOR_STR < 8) | 0x00 )

    设备返回一个字符串描述符,此描述符的结构如下:

    14USB字符串描述符(响应主机请求时返回的表示语言ID的字符串描述符)

    偏移量

    大小

         描述

    0

    bLength

    1

    N+2

    此描述表的字节数

    1

    bDescriptorType

    1

    常量

    字串描述表类型(此处应为0x03

    2

    wLANGID[0]

    2

    数字

    语言标识(LANGID 
    0

          

    N

    wLANGID[x]

    2

    数字

    语言标识(LANGID 
    X

    该字符串描述符双字节的语言ID的数组,wLANGID[0]~wLANGID[x]指明了设备支持的语言,具体含义可查看USB_LANGIDs.pdfhttp://www.baiheee.com/Documents/090518/090518112619/USB_LANGIDs.pdf

    一般来说,需要支持 0x0409,也就是标准美式英语

    索引为0的字符串索引

     2、主机根据自己需要的语言,再次向设备发出USB标准命令Get_Descriptor,指明所要求得到的字符串的索引值和语言。

    这个 USB 的 GET_DESCRIPTOR 请求的字段填充方式如下:

    bmRequestType = 0x80 (standard request -- Device Receive -- Device To Host Data)

    bRequest = 0x06 (GET_DESCRIPTOR)

    wValue = (0x03< 8) | index // ((GET_DESCRIPTOR_STR < 8) | index)

    wIndex = 0x0409 (English)

    注意,这里的 index ,就是我们第一步里面说的那三个:

    iManufacturer ,iProduct ,iSerialNumber 的值,也就是说,你想获取这3个中的哪个字符串描述,就放哪个对应的 index 进去,比如:

    iManufacturer = 0x03,iProduct = 0x02,iSerialNumber=0x01

    我想获得 Product 的字符串描述,我就这样配置我的请求:

    bmRequestType = 0x80 (standard request -- Device Receive -- Device To Host Data)

    bRequest = 0x06 (GET_DESCRIPTOR)

    wValue = (0x03< 8) | 0x02 // ((GET_DESCRIPTOR_STR < 8) | 0x02)

    wIndex = 0x0409 (English)

    这次设备所返回的是Unicode编号的字符串描述符,其结构如下:

    15Unicode字符串描述符(响应主机请求时真正表示字符串编码的字符串描述符)

    偏移量

    大小

    描述

    0

    bLength

    1

    数字

    此描述表的字节数(bString域的数值N2

    1

    bDescriptorType

    1

    常量

    字串描述表类型(此处应为0x03

    2

    bString

    N

    数字

    UNICODE 编码的字串

    最后:bString 域为设备实际返回的以UNICODE编码的字符串流,我们在编写设备端硬件驱动的时候需要将字符串转换为UNICODE编码,您可以通过一些UNICODE转换工具进行转换。

    5 USB 枚举

    当USB设备插上主机时,主机就通过一系列的动作来对设备进行枚举配置(配置是属于枚举的一个态,态表示暂时的状态),这些态如下:

            1、接入态(Attached):设备接入主机后,主机通过检测信号线上的电平变化来发现设备的接入;

            2、供电态(Powered):就是给设备供电,分为设备接入时的默认供电值,配置阶段后的供电值(按数据中要求的最大值,可通过编程设置);

            3、缺省态(Default):USB在被配置之前,通过缺省地址0与主机进行通信;

            4、地址态(Address):经过了配置,USB设备被复位后,就可以按主机分配给它的唯一地址来与主机通信,这种状态就是地址态;

            5、配置态(Configured):通过各种标准的USB请求命令来获取设备的各种信息,并对设备的某些信息进行改变或设置。

            6、挂起态(Suspended):总线供电设备在3ms内没有总线操作,即USB总线处于空闲状态的话,该设备就要自动进入挂起状态,在进入挂起状态后,总的电流功耗不超过280uA。

    5.1 获取设备描述符 GET_DESCRIPTOR

    此刻插上的 USB 设备地址还没有被配置,默认地址是0,使用 0 端点进行交互。

    总线复位及向默认地址0发送GET_DESCRIPTOR指令包,请求设备描述。第一获取描述符要先复位设备,然后等待至少100ms(100ms可以满足大多数设备),这里实际只等待了43ms。如图一所示:

    1)Index[4 - 5]:表示USB插入总线复位

    2)Index[7 - 8]:表示主机向默认地址发送GET_DESCRIPTOR指令包,详细信息也抓出来了,如图所示:

    3)Index[15 - 17]:表示设备向主机发送设备描述数据Index[16]

    4)Index[18 - 19]:表示主机完成GET_DESCRIPTOR指令后,给设备发送一个空应答;

    可以看到:数据是由二进制数字串构成的,首先数字串构成域(有七种:同步域(SYNC)、标识域(PID)、地址域(ADDR)、端点域(ENDP)、数据域(DATA)、帧号域(FRAM)、校验域(CRC)),域再构成包(比如握手包:格式如下 SYNC+PID,ACK属于PID的一种),包再构成事务(IN、OUT、SETUP,每一种事务都由令牌包、数据包、握手包三个阶段构成),事务最后构成传输(中断传输、并行传输、批量传输和控制传输)。

    可以看到, packets 96,是 DATA0 ,红色部分是带的数据,也就是前面说的 USB 请求部分:

    bmRequestType(1) + bRequest(1) + wvalue(2) + wIndex(2) + wLength(2)

    80 06 00 01 00 00 40 00

    bmRequestType=0x80,bRequest=0x06, wvalue=0x0100, wIndex=0x0000, wLength=0x0040;

    根据usb2.0协议9.4.3节描述,获取描述符时bmRequestType=0x80,bRequest=0x06,这个是协议规定固定的。

    wvalue=0x0100,高字节表示描述符类型,01表示设备,02表示配置;低字节表示索引。比如设备有多个配置,那需要读取不同配置的时候就通过低字节。或者一个配置下有多个接口,通过索引选择不同的接口。

    index=0x0000,这个参数如果为0,则不关心;如果为非零,则表示Langurage ID,每一位都有对应的意义。

    length=0x0040,表示请求的数据包长度为64.

    所以本次设置事务的目的明确了,获取设备描述符,长度为64字节。

    输入事务,是usb设备对请求进行回应,传输了16个字节的数据,为什么是传输了16个字节而不是64字节,看看偏移地址7,bMaxPacketSize0=0x10,即该设备的最大包传输大小为16字节,如果超过16字节,需要多次传输。实际设备描述符大小为18,可以看第三步的图,传输完16字节之后,主机再次发送令牌环,设备把剩下的2字节传输完成。这里我们只要获得bMaxPacketSize0 值就可以了,所以接下来直接对其进行了复位操作,否则设备还在等待传输剩余的2个字节呢。(此地,因为并不知道端点 0 的数据能力)

    struct usb_device_descriptor {
    u8 bLength;
    u8 bDescriptorType;
    u16 bcdUSB;
    u8 bDeviceClass;
    u8 bDeviceSubClass;
    u8 bDeviceProtocol;
    u8 bMaxPacketSize0;
    u16 idVendor;
    u16 idProduct;
    u16 bcdDevice;
    u8 iManufacturer;
    u8 iProduct;
    u8 iSerialNumber;
    u8 bNumConfigurations;
    } __attribute__ ((packed));

    输出事务:因为获取描述符之前把设备包大小的初始值设为了64,所以输入事务之后,就认为传输完成,主机发送了一个输出事务,响应设备,已经收到数据。

    5.2 设置地址SET_ADDRESS

    再次复位总线及向设备发送SET_ADDRESS指令包,设置设备地址。如图二所示:

    1)Index[22 - 23]:表示再次总线复位,该复位自动完成,不是手工插拔USB完成
    2)Index[25 - 27]:表示主机向默认地址发送SET_ADDRESS指令包,详细信息如图所示:

    设置地址为1

    3)Index[29 - 31]:表示设备完成SET_ADDRESS指令后,给主机发送一个空应答;

    设置地址为0x0002,由于我是从网上找的图,所以两幅图地址设置的不一样,这里注意一下

    5.3 请求设备描述 GET_DESCRIPTOR

    向第二步设定的设备地址发送GET_DESCRIPTOR指令包,请求设备描述。

    1)Index[33 - 35]:表示主机向地址01发送GET_DESCRIPTOR指令包,详细信息如图

    2)Index[41 - 43]:表示设备向主机发送设备描述数据Index[42]
    3)Index[45 - 47]:表示设备向主机发送设备描述数据Index[46]
    4)Index[48 - 50]:表示主机完成GET_DESCRIPTOR指令后,给设备发送一个空应答

    5.4 请求配置描述 GET_DESCRIPTOR

    向第二步设定的设备地址发送GET_DESCRIPTOR指令包,请求配置描述

    1)Index[52 - 54]:表示主机向地址01发送GET_DESCRIPTOR指令包,详细信息如图所示

    2)Index[57 - 59]:表示设备向主机发送配置描述数据Index[58]
    3)Index[60 - 62]:表示主机完成GET_DESCRIPTOR指令后,给设备发送一个空应答;

    获得数据:

    09 02 2E 00 01 01 00 60 01

    解析输入事件获取的配置信息:

    struct usb_configuration_descriptor {
    u8 bLength; /*09,描述符长度为9*/
    u8 bDescriptorType;/* 0x2, 表示配置描述符*/
    u16 wTotalLength; /*0x002E,表示当前配置下的各种描述信息总长度为46*/
    u8 bNumInterfaces; /*0x01,当前配置下共一个接口*/
    u8 bConfigurationValue; /*0x01,当前配置索引,当设置某一配置时,给SetConfiguration(x)传递的参数*/
    u8 iConfiguration;/*0x00,字符串描述索引*/
    u8 bmAttributes;/*0x60,属性信息*/
    u8 bMaxPower;/*0x01当前配置最大消耗电流*/
    } __attribute__ ((packed));

    5.5 读取完整设备描述及配置描述

    再次读取配置描述符,读取长度 wTotalLength 46字节。

    09 02 2E 00 01 01 00 60 01 和第四步获得的一样

    09 04 00 00 04 00 00 00 00 描述符长度也是09,04表示是一个接口描述符

    07 05 81 03 08 00 c8 描述符长度为07,05表示端点描述符

    07 05 01 03 08 00 c8

    07 05 82 02 40 00 00

    07 05 02 02 40 00 00

    接口描述符详解:

    struct usb_interface_descriptor {
    u8 bLength; /*0x09,描述符长度*/
    u8 bDescriptorType;/* 0x04 ,表示接口描述符*/
    u8 bInterfaceNumber; /*0,接口号为0*/
    u8 bAlternateSetting; /*0,接口的可选设置*/
    u8 bNumEndpoints; /*04,当前接口共4个端点*/
    u8 bInterfaceClass; /*0*/
    u8 bInterfaceSubClass;/*0*/
    u8 bInterfaceProtocol; /*0*/
    u8 iInterface; /*0*/
    } ;

    端点描述符详解:

    struct usb_endpoint_descriptor {
    u8 bLength; /*07,描述符长度*/
    u8 bDescriptorType;/* 0x5 ,表端点描述符*/
    u8 bEndpointAddress;/*0x81,bit[7] =1,表示输入端点,0表示输出端点;bit[6:4],保留;bit[3:0]端点号,为1*/
    u8 bmAttributes;/*0x03,bit[1:0]=11,表传输类型为中断传输*/
    u16 wMaxPacketSize;/*0x0008,当前端点最大发送和接收包大小*/
    u8 bInterval;/*0xc8,查询时发送数据的间隔时间*/
    } ;

    5.6 配置设备 SET_CONFIGURATION

    向第二步设定的设备地址发送SET_CONFIGURATION指令包,设置配置描述。

    1)Index[139 - 141]:表示主机向地址01发送SET_CONFIGURATION指令包,详细信息如下:

    2)Index[143 - 145]:表示设备完成 SET_CONFIGURATION 指令后,给主机发送一个空应答
    至此,枚举过程结束,设备可通过驱动与主机通信了。

    /* device request (setup) */
    struct devrequest {
    unsigned char requesttype; /*0x00,表请求设置*/
    unsigned char request; /*0x09,表示设置配置*/
    unsigned shortvalue; /*0x0001,使用配置,必须匹配从配置描述符都过来的bConfigurationValue*/
    unsigned shortindex; /*0x0000,协议规定设为0*/
    unsigned shortlength; /*0x0000,协议规定设为0*/
    } __attribute__ ((packed));

    USB枚举过程:

    0 插入设备

    1 获取USB设备的设备描述符 : 使用默认地址0,使用稍微长一些的数据长度(比如:0x40)

    2 成功后复位设备

    3 对设备进行地址设置  : 使设备从地址状态进入寻址状态

    4 再次获取设备描述符 : 使用新的地址

    5 获取设备配置符

    6 根据设备配置符中的配置符总长度,获取其他配置符(接口,端点等)

    7 设置配置 : 使设备从地址状态进入配置状态

    展开全文
  • 沈阳广成科技有限公司,型号USBCAN-I Bas,可运行广成科技ECAN Tools、周立功CAN Test软件,可通过软件加载DBC文件进行数据解析。...该型号设备适用于CAN总线学习、调试、数据收发、数据监测、数据分析等用途。
  • usbcan、can分析仪的产品特点和功能特点 来可的usbcan、can分析仪usb接口can卡具有一体便携式、小巧、真材实料、工业四级、软件命令开关内置式终端电阻、三种接口方式供选等特点。 1、小巧、一体便携式 市面上usb...
  • 本文介绍了一种不用USB逻辑分析仪(TOTALPHASE Beagle USB480ProtocolAnalyzer)就可以分析USB协议的免费解决方案。 方案:usbmon+tcpdump+wireshark usbmon:将USB总线上的数据输出出来,没有它你就取不到总线上的...
  • USBCAN-C系列便携式车用CAN分析仪,通过USB接口快速扩展一路CAN通道,使接入CAN网络非常容易,它具有一体式和小巧紧凑的外形,特别适合于随身携带。CAN接口采用金升阳电源模块和信号隔离芯片实现2500V DC电气隔离,...
  • USB2.0协议分析

    千次阅读 2017-08-22 15:25:12
    一、USB硬件介绍1.1 概述一条USB传输线分别由地线、电源线、D+和D-四条线构成,D+和D-是差分输入线,它使用的是3.3V的电压(与CMOS的5V电平不同),而电源线和地线可向设备提供5V电压,最大电流为500mA(可以在编程中...
  • Bus Hound是一个超级软件总线协议分析器,用于捕捉来自设备的协议包和输入输出操作,其优良特性如下: 支持所有版本的IDE,SCSI,USB,1394总线 支持各类设备如硬盘库,DVD,鼠标,扫描,网络照相机等 捕捉数据...
  • 名称:纬图Ginkgo2 Mini USB-CAN总线适配器品牌:ViewTool/纬图型号:VTG212A 典型应用: - 通过PC的USB或智能设备USB的CAN总线数据发送和接收 - CAN网络数据采集、数据分析 - USB接口转CAN网络接口 - 延长CAN总线...
  • https://mbb.eet-china.com/blog/3918459-415692.html
  • USB总线专题(一)——基础知识

    千次阅读 多人点赞 2017-08-21 10:49:08
    1.基本概念介绍USB (Universal Serial Bus)是1995年Microsoft、Compaq、IBM等公司联合制定的一种新的PC串行通信协议。它基于通用连接技术,实现外设的简单快速连接,达到方便用户、降低成本、扩展PC连接外设范围的...
  • USBCAN系列便携式CAN分析仪,通过USB接口快速扩展一路CAN通道,使接入CAN网络非常容易,它具有一体式和小巧紧凑的外形,特别适合于随身携带。CAN接口采用金升阳电源模块和信号隔离芯片实现2500V DC电气隔离,USB接口...
  • IIC 协议分析 梦源实验室 10月21日 协议基础 1.1. 协议简介 IIC-BUS(Inter-IntegratedCircuit Bus)最早是由PHilip半导体(现在被NXP收购)于1982年开发。主要是用来方便微控制器与外围器件的数据传输。它是一种...
  • 串口RS232/485/UART转CANbus总线转换器网关CSM100模块CANCOMCANUART-100T产品简介产品优势产品特性产品规格引脚定义和尺寸 CANUART-100T 产品简介 CANUART-100T系列智能双向UART转CAN模块具有一路TTL UART串口通道和...
  • 名称:纬图Ginkgo USB-CAN接口适配器品牌:ViewTool/纬图型号:VTG203B 典型应用: - 通过PC的USB接口对CAN总线网络...- CAN总线USB网关,延长CAN总线的网络通讯长度 - USB接口转CAN网络接口 产品特色 - 支持L...
  • CAN总线接口协议分析 通过OSC482L进行CAN总线接口的分析,仪器可选多种测量方式,可以支持单线或双线方式测量。单线测试测量可以支持自动,CAN_H对地,CAN_L对地三种方式,双线差分方式测量支持自动,和A-B通道差分...
  • USB协议详解

    万次阅读 多人点赞 2019-03-13 14:58:11
    本博客整理自网络,仅供学习参考,如有侵权,联系删除。... 一个transfer(传输)由一个或多个transaction(事务)构成,一个transaction...USB的数据通讯首先是基于传输(transfer)的,传输的类型有:中断传输、批量传输...
  • USB转LIN,USB转CAN,USB转PWM,总线工具

    千次阅读 2019-05-08 18:58:24
    在开发LIN总线接口的产品时,往往是需要USB转LIN适配器来协助产品开发的,比如通过上位机端发送LIN数据,读取LIN数据,监控LIN总线数据,同时也需要使用ldf文件进行协议解析,模拟从机或者模拟主机对从机进行控制。...
  • 从调试数据分析USB通信协议——USB键盘鼠标【HID类设备】(四) 平时我们在使用USB设备的时候,除了U盘使用的比较多以外,USB人体输入学设备,更是必不可少的存在,如鼠标,键盘。这里小编我也来简述一下HID[Human ...
  • 第二篇 USB2.0协议简述(包-事务-传输)

    千次阅读 2020-11-03 10:32:11
    一、 USB2.0通信协议简介 1. 包(Package) 包是USB传输的基本单元,USB协议规定了三种类型的包:令牌(Token)包、数据(DATAx)包、握手(Ack)包。其中,令牌包只能是从主机发出。数据包和握手包可由主机发出,也可是...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 2,393
精华内容 957
关键字:

usb总线协议分析仪