一、问题原因
调试前的预备
二、调试前预备
调试之前花了三天的时刻,大致的看了一下USB的结构,后来才发现,没什么必要,不过多学点常识总是好的。
效果:USB体系用来首要进行查询装备和给USB设备发送通用的指令,它要确保数据传输进程的数据完整性。设备枚举进程中的各种设备描绘符的获取以及设置地址、设置装备都是经过操控传输来完结的。特色:操控传输是双向传输,数据量一般较小;数据传送是无损性的。
仅批量传输协议中规则了两个特别的类恳求:bulk-only Mass Storage Reset 和Get Max LUN,前者是复位到指令状况的恳求,后者是获取最大逻辑单元的恳求。
usb协议中选用的是小端格局,这一点要分外留意,比方ASCII 0x55、0x53,用小端格局一共便是0x5355
bmRequestType为0xa1,一共它是发送到接口的类输入恳求,bRequest为0xfe,wIndex为恳求的接标语,传输的数据长度为1字节,设备将在数据进程回来1字节的数据,一共设备有多少个逻辑单元,0一共1个逻辑单元,1一共有两个。
2.bulk-only Mass Storage Reset 的格局如下图
bulk-only Mass Storage Reset恳求是告诉设备接下来的批量端点输出数据为指令快封装包CBW(Command Block Wrapper),在这个恳求中,仅需求设置一下状况,阐明接下来的数据是CBW,然后回来一个长度为0的状况数据包。
3.仅批量传输的的数据流
类恳求完结后,就进入了数据传输进程,在仅批量数据传输协议中规则,数据传输分为三个阶段:指令阶段、数据阶段和状况阶段。指令阶段是由主机经过批量端点发送一个CBW(指令封装包)的结构,在CBW中界说了要操作的指令以及传输数据的方向和数量,数据阶段的传输方向由指令阶段决议,而状况阶段则总是由设备回来该指令完结的状况。
CBW的结构如下图
官方文档对这些字段的介绍:
dCBWSignature:
Signature that helps identify this data packet as a CBW. The signature field shall contain the value
43425355h (little endian), indicating a CBW.
dCBWTag:
A Command Block Tag sent by the host. The device shall echo the contents of this field back to the
host in the dCSWTag field of the associated CSW. The dCSWTag positively associates a CSW with the
dCBWDataTransferLength:
The number of bytes of data that the host expects to transfer on the Bulk-In or Bulk-Out endpoint (as
bmCBWFlags:
The bits of this field are defined as follows:
Bit 7 Direction – the device shall ignore this bit if the dCBWDataTransferLength field is
zero, otherwise:
0 = Data-Out from host to the device,
1 = Data-In from the device to the host.
Bit 6 Obsolete. The host shall set this bit to zero.
Bits 5..0 Reserved – the host shall set these bits to zero.
bCBWLUN:
The device Logical Unit Number (LUN) to which the command block is being sent. For devices that
support multiple LUNs, the host shall place into this field the LUN to which this command block is
addressed. Otherwise, the host shall set this field to zero.
bCBWCBLength:
The valid length of the CBWCB in bytes. This defines the valid length of the command block. The
only legal values are 1 through 16 (01h through 10h). All other values are reserved.
CBWCB:
The command block to be executed by the device. The device shall interpret the first bCBWCBLength
bytes in this field as a command block as defined by the command set identified by bInterfaceSubClass .
If the command set supported by the device uses command blocks of fewer than 16 (10h) bytes in
length, the significant bytes shall be transferred first, beginning with the byte at offset 15 (Fh). The
device shall ignore the content of the CBWCB field past the byte at offset (15 + bCBWCBLength – 1).
指令封装包CSW
dCSWSignature:
Signature that helps identify this data packet as a CSW. The signature field shall contain the value
53425355h (little endian), indicating CSW.
dCSWTag:
The device shall set this field to the value received in the dCBWTag of the associated CBW.
bCSWStatus:
bCSWStatus indicates the success or failure of the command. The device shall set this byte to zero if
the command completed successfully. A non-zero value shall indicate a failure during command
execution according to the following table:
Value Description
00h Command Passed (“good status”)
01h Command Failed
02h Phase Error
03h and 04h Reserved (Obsolete)
05h to FFh Reserved
界说一个缓冲区用来接纳指令块封装包CBW,然后进入到数据处理阶段,在数据处理中,对CBW进行解码,回来或许接纳呼应的数据。数据发送或许接纳完毕后,进入到状况阶段,回来指令碑文的状况,然后再次进入指令阶段,等候主机发送CBW包。
3.SCSI指令集
小型计算机体系接口(英语:Small Computer System Interface; 简写:SCSI),一种用于计算机和智能设备之间(硬盘、软驱、光驱、打印机、扫描仪等)体系级接口的独立处理器标准。 SCSI是一种智能的通用接口标准。它是各种计算机与外部设备之间的接口标准。
在U盘中经常用到的指令有:INQUIRY、READ CAPACITY 、READ(10)、WRITE(10)指令等。
INQUIRY指令恳求查询方针设备的一些基本信息,操作码为0x12,。
READ FORMAT CAPACITIES指令能够让主机读取设备各种或许的格局化容量的列表,假如设备中没有存储设备,则设备回来最大能够支撑的格局化容量。
读容量指令READ CAPACITY能够让主机读取到当时存储前言的容量,操作代码为0x25,READ CAPACITY读取的是实践的磁盘容量。
主机运用READ(10)指令来读取实践磁盘的数据,运用WRITE(10)交游设备中写入实践的磁盘数据。
4.STM32 相关常识
STM32供给的有USB全速设备接口,支撑USB全速总线、USB挂起/康复操作,能够中止设备时钟完结低功耗。USB和CAN共用一个专用的512字节的SRAM存储器用于数据的发送和接纳,不能一起运用USB和CAN总线。
PC主机和微操控器之间的数据传输是经过同享这一专用的数据缓冲区来完结的,数据缓冲区能被USB外设直接拜访。这块专用数据缓冲区的巨细由所运用的端点数目和每个端点最大的数据分组巨细所决议,每个端点最大可运用512 字节缓冲区,最多可用于16个单向或8 个双向端点。USB模块同PC主机通讯,依据USB标准完结令牌分组的检测,数据发送/ 接纳的处理,和握手分组的处理。整个传输的格局由硬件完结,其间包含CRC的生成和校验。每个端点都有一个缓冲区描绘块,描绘该端点运用的缓冲区地址、巨细和需求传输的字节数。 当USB模块辨认出一个有用的功用/ 端点的令牌分组时,( 假如需求传输数据并且端点已装备) 随之产生相关的数据传输。USB模块经过一个内部的16位寄存器完结端口与专用缓冲区的数据交换。在一切的数据传输完结后,假如需求,则依据传输的方向,发送或接纳恰当的握手分组。在数据传输完毕时,USB模块将触发与端点相关的中止,经过读状况寄存器和/ 或许运用不同的中止处理程序,微操控器能够确认
● 哪个端点需求得到服务
● 产生如位填充、格局、CRC、协议、缺失ACK、缓冲区溢出/ 缓冲区未满等过错时,正在进行的是哪种类型的传输。
USB模块对同步传输和高吞吐量的批量传输供给了特别的双缓冲区机制,在微操控器运用一个缓冲区的时分,该机制确保了USB外设总是能够运用另一个缓冲区。在任何不需求运用USB模块的时分,经过写操控寄存器总能够使USB模块置于低功耗形式(SUSPEND形式) 。在这种形式下,不产生任何静态电流耗费,一起USB时钟也会减慢或中止。经过对USB线上数据传输的检测,能够在低功耗形式下唤醒USB模块。也能够将一特定的中止输入源直接连接到唤醒引脚上,以使体系能当即康复正常的时钟体系,并支撑直接发动或中止时钟体系。
三、例程剖析
1.首要进行体系装备,如时钟、USB、NAND FLASH、SD卡的初始化等
USB低优先级中止(通道20):可由一切USB事情触发(正确传输,USB复位等)。固件在处理中止前应当首要确认中止源。中止处理函数为:USB_Istr
USB高优先级中止(通道19):仅能由同步和双缓冲批量传输的正确传输事情触发,意图是确保最大的传输速率。它的中止处理函数是CTR_HP。
阐明:函数CTR_HP和CTR_LP终究都会调用Mass_Storage_In(端点1)和Mass_Storage_Out(端点2)两个函数来和PC端的USB HOST 通讯
为了让SD I/O卡能够中止多媒体卡/SD 模块,在SD接口上有一个具有中止功用的引脚——第8脚,在4 位SD形式下这个脚是SDIO_D1,卡用它向多媒体卡/SD 模块提出中止恳求。关于每一个卡或卡内的功用,中止功用是可选的。SD I/O的中止是电平有用,即在被辨认并得到多媒体卡/SD 模块的呼应之前,中止信号线有必要坚持有用电平( 低) ,在中止进程完毕后坚持无效电平(高)。在多媒体卡/SD 模块服务了中止恳求后,经过一个I/O 写操作,写入恰当的位到SD I/O卡的内部寄存器,即可铲除中止状况位。一切SD I/O卡的中止输出是低电平有用,多媒体卡/SD 模块在一切数据线(SDIO/D[3:0])上供给上拉电阻。多媒体卡/SD 模块在中止阶段对第8 脚(SDIO_D/IRQ) 采样并进行中止检测,其它时刻该信号线上的数值将被疏忽。
4.进入while循环,等候中止的产生
主机发送Get Max LUN恳求,获取最大逻辑单元。
主机经过批量端点发送CBW包,在CBW中界说了要操作的指令以及传输数据的方向和数量,回来该指令完结的状况,即由设备回来CSW包,端点2用于输出,端点1用于输入数据至主机。CBW的标志是0x55,0x53,0x42,0x43。
在USB主机和设备的通讯进程中,数据会先被放到一个巨细为512字节的专用SRAM缓冲区晒干,然后再传输到主机或许USB设备。
四、例程问题现象和解决方法
1.NAND FLASH盘能够被辨认,格局化失利。已然NAND FLASH盘能够被辨认,那就标明USB的操控传输没呈现问题,USB批量传输出问题了,并且最或许的是NAND FLASH的驱动有问题,细心看完代码,发现在树立坏块表,对Spare 区域进行读操作中,对NAND FLASH 有一个NAND_CMD_AREA_TRUE1指令操作,检查代码,
#define NAND_CMD_AREA_TRUE1
2.SD盘也能被辨认,不能格局化。开端用的是2G的SD卡,后来测验1G和512M的,它们都能用,也便是说,这个SD卡驱动只辨认1G和512M的SD卡。
在代码中增加调试信息,结果是写入的块长度犯错。经过对读SD卡信息了解到,2G的SD卡,块巨细是1024字节,其它的卡都是512字节。我在SDIO例程中设置块巨细为1024字节,读写犯错,设置512字节,居然是正确的。
USB MassStorage例程中是首要从SD卡中读取SD卡块巨细的值,依照这个值来读写SD卡,而实践上2G的SD卡只能依照512字节来读写。所以在读取块巨细的值后,把块的巨细除以2,块数目乘以2,卡的总容量不变,程序运转后,一切正常了。