<br />前些时候做了一个项目,其中要实现USB的功能,包括U盘的读写和使用USB鼠标键盘。经过一段时间的调试终于完工了。现在将一些关键的调试点记下来,一方面大概整理一下自己思路,另一方面希望能给正在做类似工作的兄弟们一些参考,希望对大家能有所帮助。<br /><br />我的系统是linux 2.6,USB的主控制器采用了爱普生的S1R72V17,USB的驱动代码由爱普生公司提供。在开始工作之前,我先从爱普生的网站上下载了相关的资料,包括这款芯片的datasheet和硬件设计文档以及软件移植文档。<br /><br />(资料下载网址:http://www.epson.jp/device/semicon_e/product/interface/index.htm)<br /><br />在这个项目的过程中,我的主要工作是完成硬件的设计和调试,并且将爱普生提供的linux 2.6的驱动移植到我的系统中。<br /><br />USB的硬件系统设计比较简单(参考下图),通过地址数据总线和CPU相连,另外USB控制器有一个中断信号要接入CPU系统。S1R72V17需要3个不同的电压分别是3.3v, 1.8v和5v。另外一部分电路是关于USB的接口电路,包括差分信号线对和过流保护电路。除此之外72v17还需要一个时钟,这个时钟可以由12M的晶体提供也可以由24M或者48M的有源晶振提供。<br />http://space.**/upload/2008/7/22/d649d836-ed9d-4ad3-b9ca-504a7b7dc05f.JPG<br />在硬件电路设计过程中,比较关键的是总线的接法以及差分信号线对的走线。72V17有3种总线访问模式,分别是8bits模式、16bits BE模式以及16bits strobe模式,BE模式需要CPU端提供WBEL和WBEH信号来分别访问高低字节,strobe模式需要CPU端提供WRH和WRL信号来分别访问高低字节。差分信号线对的布线需要注意以下几点:<br /><br />1> 差分阻抗90欧<br /><br />2> DM/DP尽量短,使得信号传输延时保持在1ns以下<br /><br />3> 两条线必须平行,并且等长<br /><br />4> 这两条线下面的PCB层,必须是整块地,不能有分割<br /><br />5> 避免在这两条线附件走线。尤其是高速信号和时钟信号要远离这对线<br /><br />6> 如果不能一直走直线,那么可以在拐点出走弧线,以减小信号反射<br /><br />7> VBUS线必须远离DP/DM<br /><br />8> 如果信号线有分叉或者线上有其它器件接入,一定要确保匹配的阻抗<br /><br />9> 信号线上不要打过孔<br /><br />10> 推荐使用防静电和浪涌的保护器件<br /><br />爱普生的网站上提供了72V17在linux2.6.14下的驱动代码,以及相应的移植手册。由于我的系统恰好就是2.6.17的版本,加上驱动说明手册比较详细,所以软件移植上去没有费太大力气。其中比较关键的是寄存器访问,其它的只要按照移植手册设置就可以了。<br />http://space.**/upload/2008/7/22/47efd230-53c5-41f1-a89b-5ba6758bf6a9.JPG<br />上图是linux下的USB系统的结构框图,USB core 和Class层不需要做改动,而爱普生提供的驱动代码就是usb host controller driver层。<br /><br />下面是驱动文件的说明:<br />http://space.**/upload/2008/7/22/f94ab2ee-d83d-4b66-bce6-b0c26999d614.JPG<br />软件的移植工作量并不大,首先需要改动USB的makefile和kconfig。<br /><br /> 在driver/usb/host/Kconfig中加入下面配置<br /><br /> Config USB_V17_HCD<br /><br /> tristate “S1R72V17 HCD support”<br /><br /> depends on USB<br /><br /> default Y<br /><br /> 在driver/usb/Makefile中加入下面的内容<br /><br /> obj-$(CONFIG_USB_V17_HCD)+=host/<br /><br /> obj-$(CONFIG_USB_V17_HCD)+=s1r72v17-hcd.o<br /><br /><br /><br />接着需要改动系统配置,在arch/arm/mach-s3c2410/mach-star.c中加入<br /><br />//for EPSON Start<br /><br />static struct resource s1r72xxx_ohci_resources[] = {<br /><br /> [0] = {<br /><br /> .start = 0x28000000,<br /><br /> .end = 0x2c000000,<br /><br /> .flags = IORESOURCE_MEM,<br /><br /> },<br /><br /> [1] = {<br /><br /> .start = IRQ_EINT5,<br /><br /> .end = IRQ_EINT5,<br /><br /> .flags = IORESOURCE_IRQ,<br /><br /> },<br /><br />};<br /><br />static u64 v17_dma_mask = 0xffffffffUL ;<br /><br />static struct platform_device epson_ohci_device = {<br /><br /> .name = "s1r72v17",<br /><br /> .id = -1,<br /><br /> .dev = {<br /><br /> .dma_mask = &v17_dma_mask,<br /><br /> .coherent_dma_mask = 0xffffffffUL,<br /><br /> },<br /><br /> .num_resources = ARRAY_SIZE(s1r72xxx_ohci_resources),<br /><br /> .resource = s1r72xxx_ohci_resources,<br /><br />};<br /><br />//for EPSON End<br /><br /> <br /><br />最后要对Linux系统进行配置,使用make menuconfig进行如下配置。<br /><br /> HCD driver<br /><br /> Device Drivers -><br /><br /> USB support -><br /><br /> <*> V17_HCD support.<br /><br /> <*> USB Mass Storage support<br /><br /><>USB Human Interface Device (full HID) support<br /><br /> USB HID Boot protocol driver -><br /> <*> USB HIDBP keyboard(simple boot) support<br /><br /> <*> USB HIDBP Mouse (simple boot) support<br /><br /> Device Driver -><br /><br /> Block devices<br /><br /> <*> Low Performance USB Block driver<br /><br /> http://space.**/upload/2008/7/22/a9509abc-33fb-42f4-8a11-389ab8137e1f.JPG<br /><br />如果寄存器访问没有问题的话就可以进行编译了。<br /><br />OK! 将编译好的image文件下到板子上,系统的USB功能就实现了。插上U盘试一试,超级终端将会出现下面的信息。<br /><br />bash-2.05a# hub.c: USB new device connect on bus1/1, assigned device number 2 usb_get_device_descriptor!!!<br /><br />scsi0 : SCSI emulation for USB Mass Storage devices<br /><br /> Vendor: Generic Model: USB Flash Drive Rev: %z!Y<br /><br /> Type: Direct-Access ANSI SCSI revision: 02<br /><br />Attached scsi removable disk sda at scsi0, channel 0, id 0, lun 0 SCSI device sda: 254720 512-byte hdwr sectors (130 MB)<br /><br />sda: Write Protect is off<br /><br />Partition check:<br /><br />sda:<7>usb-storage: queuecommand() called<br /><br />sda1 sda2 sda3 sda4<br /><br />使用mount就可以对U盘进行读写了。除此之外USB鼠标和USB键盘也可以工作。 |
|