1.Linux usb设备驱动框架
USB是通用串行总线的总称,Linux内核几乎支持所有的usb设备,包括键盘,鼠标,打印机,modem,扫描仪。Linux的usb驱动分为主机驱动与gadget驱动。前者是设备连接到计算机上,通过主机驱动扫描usb设备,控制所连接的设备。而gadget驱动一般用于嵌入式设备,gadget驱动用于控制嵌入式设备。Linux的usb驱动两种类型图如下:
左侧是usb的主机驱动,右侧是gadget驱动。下面着重介绍一下usb的主机驱动:
(1)usb主机控制器-直接与硬件设备交互。
(2)usb core-向usb设备驱动提供API以及usb主机控制器驱动的程序。使用usb core所提供的函数,宏来完成数据处理的功能。
(3)usb设备驱动,即usb接口驱动,一般所说的usb驱动指的是usb接口驱动
2.usb系统的组成部分
usb系统一般由三个部分组成,主机,一个或多个usb hub,以及与之些hub连接的usb设备。
(1)主机
在任何的usb系统中仅有一个主机,主机系统中的usb接口即上图中的主机控制器,主机控制器可由硬件,软件或固件组成。主机主要负责:
a.检测usb设备的连接与拆除
b.管理主机与usb设备之间的控制流
c.管理主机与usb设备之间的数据流
d.收集状态和活动的统计
e.为连接的usb设备提供电源
(2)usb设备
所有的usb设备都是通过地址来存取的,这个地址在连接或枚举时分配。usb设备对usb系统来说是端点的集合,一组端点实现一个接口。设备端点是usb设备中唯一可寻址的部分。它是主机与设备之间通信流的结束点。一系列的相互独立的端点构成了usb逻辑设备。每个端点支持流进设备或者是流出设备。
主机与设备端点上的usb数据传输是通过管道的方式。
(3)hub
所有的usb device都连接在hub端口上。
3. usb传输模式
(1)控制传输模式(Control)
控制传输模式支持双向传输,用来处理从usb主机端口到usb设备端口的数据传输,用于控制指令,设备状态查询以及确认命令。
(2)等时传输方式(lsochronous )
等时传输是一种周期性的连续性的意向传输模式,通常用于对时间有着密切关系的信息的传输,对准确性要求不高,但对时间要求极为敏感的设备,如视频,音频的传输。
(3)中断传输模式(Interrupt)
中断传输模式用于非周期性的,自然发生的,数据量小的传输,数据传输的方向是从设备到主机。如usb键盘和鼠标
(4)批量传输模式(bulk)
批量传输模式是一种单向的,用于大量数据传输的模式,该方式用来传输正确无误的数据。通常打印机,扫描仪,数码相机以这种方式与主机连接
4. usb设备组成
(1)一个usb设备由可以有一个或多个配置
(2)一个配置通常可以有一个或多个接口
(3)一个接口通常可以有一个或多个端点
通常所尽的usb设备驱动是指接口驱动,即一个接口对应一个驱动。
所以Linux usb设备有四大描述符,分别为设备描述符,配置描述符,接口描述符,端点描述符。下面看一个这几个描述符的相关数据结构:
struct usb_device_descriptor
{ _u8 bLength; //此描述符的字节数 _u8 bDescriptorType; //描述符的种类为设备 _u16 bcdUSB; //此设备与描述符兼容的usb设备说明版本号(BCD码) _u8 bDeviceClass; //设备类码 _u8 bDeviceSubClass; //设备子类码 _u8 bDeviceProtocol; //协议码 _u8 bMaxPacketSize0; //端点0的最大包大小 _u16 idVendor; //厂商标志 _u16 idProduct; //产品标志 _u16 bcdDevice; //设备发行号 _u8 iManufacturer; //描述厂商的字串索引
_u8 iProduct; //描述产品信息的字串索引
_u8 iSerialNumber; //描述设备序列号信息的字串索引 _u8 bNumConfigurations;//此设备支持的配置数
}_attribute_ ((packed));
设备类码的典型值如下:
#define USB_CLASS_PER_INTERFACE 0
#define USB_CLAS_AUDIO 1 //声音设备
#define USB_CLASS_COMM 2 // 调制解调器,网卡,ISDN连接
#define USB_CLASS_HID 3 //HID设备,如鼠标,键盘
#define USB_CLASS_PHYSICAL 5 //物理设备
#define USB_CLASS_STILL_IMAGE 6 //静止图像捕捉设备
#define USB_CLASS_PRINTER 7//打印机
#define USB_CLASS_MASS_STORAGE //8 批量存储设备
#define USB_CLASS_HUB 9 //USB HUBS
#define USB_CLASS_CSCID 0x0B //智能卡
#define USB_CLASS_VIDEO 0X0E //视频设备,如网络摄像头
#define USB_CLASS_VENDOR_SPEC 0xFF //厂商自定义的设备
struct usb_config_descriptor{
_u8 bLength ;//此描述符的字节数
_u8 bDescriptorType; //配置描述符类型
_u16 wTotalLength; //此配置信息的总长(包括配置,接口,端点和设备类型及厂商定义的描述符)
_u8 bNumInterfaces; //此配置所支持的接口数
_u8 bConfigurationValue ;//在setConfiguration()请求中用作参数来选定此配置
_u8 iConfiguration; //描述此配置的字串描述符索引
_u8 bmAttributes; //电源配置特性
_u8 bMaxpowe;r //此配置下的总线电源耗电量
}_attribute_ ((packed));
配置描述符给出了usb设备配置信息,以及此配置下的接口数。每个接口可能的独立操作。
struct usb_interface_descriptor{
_u8 bLength ;//此描述符的字节数
_u8 bDescriptorType;//接口描述符类
_u8 bInterfacNumber;//接口号,当前配置所支持的接口数组索引,从0开始
_u8 bNumEndpoints ;//此接口用的端点数量,如果是0,说明此接口只有缺省控制通道
_u8 bAlernateSetting;//可选设备的索引值
_u8 bInterfaceClass;// 类值,0值作为将来保留使用如果是0FFH,此接口由厂商说明
_u8 bInterfaceSubClass;//子类码
_u8 bInterfaceProtocol;//协议码
_u8 iInterface;//描述此接口的字串描述符索引
}_attribute_ ((packed));
struct usb_endpoint_descriptor{
_u8 bLength ;//此描述符的字节数
_u8 bDescriptorType;//端点描述符类
_u8 bEndpointAddress;此描述符所描述的端点的地址
_u8 bmAtrributes;//所指定的端点的特性,如果是00=控制传送,01=等时传送,10=批传送,11=中断传送
_u8 wMaxPacketSize;//当前配置下端点能够发送与接收的最大数据包大小
_u8 bInterval;//轮询数据传送端点的时间间隙
_u8 bRefresh
_u8 bSynchAddress
}_attribute_ ((packed));
以上给出了usb中的设备描述符,配置描述符,接口描述符和端点描述符。
5. usb设备驱动的几个重要的数据结构
usb_driver,usb_device,usb_bus.
/** 788 * stru ct usb_driver - identifies U SB interface driver to u sbcore 789 * @name: The driver name shou ld be u niqu e among U SB drivers, 790 * and shou ld normally be the same as the modu le name. 791 * @probe: Called to see if the driver is willing to manage a particu lar 792 * interface on a device. If it is, probe retu rns zero and u ses 793 * u sb_set_intfdata() to associate driver-specific data with the 794 * interface. It may also u se u sb_set_interface() to specify the 795 * appropriate altsetting. If u nwilling to manage the interface, 796 * retu rn -ENODEV, if genu ine IO errors occu red, an appropriate 797 * negative errno valu e. 798 * @disconnect: Called when the interface is no longer accessible, u su ally 799 * becau se its device has been (or is being) disconnected or the 800 * driver modu le is being u nloaded. 801 * @u nlocked_ioctl: U sed for drivers that want to talk to u serspace throu gh 802 * the "u sbfs" filesystem. This lets devices provide ways to 803 * expose information to u ser space regardless of where they 804 * do (or don't) show u p otherwise in the filesystem. 805 * @su spend: Called when the device is going to be su spended by the system. 806 * @resu me: Called when the device is being resu med by the system. 807 * @reset_resu me: Called when the su spended device has been reset instead 808 * of being resu med. 809 * @pre_reset: Called by u sb_reset_device() when the device 810 * is abou t to be reset. 811 * @post_reset: Called by u sb_reset_device() after the device 812 * has been reset 813 * @id_table: U SB drivers u se ID table to su pport hotplu gging. 814 * Export this with MODU LE_DEVICE_TABLE(u sb,...). This mu st be set 815 * or you r driver's probe fu nction will never get called. 816 * @dynids: u sed internally to hold the list of dynamically added device 817 * ids for this driver. 818 * @drvwrap: Driver-model core stru ctu re wrapper. 819 * @no_dynamic_id: if set to 1, the U SB core will not allow dynamic ids to be 820 * added to this driver by preventing the sysfs file from being created. 821 * @su pports_au tosu spend: if set to 0, the U SB core will not allow au tosu spend 822 * for interfaces bou nd to this driver. 823 * @soft_u nbind: if set to 1, the U SB core will not kill U RBs and disable 824 * endpoints before calling the driver's disconnect method. 825 * 826 * U SB interface drivers mu st provide a name, probe() and disconnect() 827 * methods, and an id_table. Other driver fields are optional. 828 * 829 * The id_table is u sed in hotplu gging. It holds a set of descriptors, 830 * and specialized data may be associated with each entry. That table 831 * is u sed by both u ser and kernel mode hotplu gging su pport. 832 * 833 * The probe() and disconnect() methods are called in a context where 834 * they can sleep, bu t they shou ld avoid abu sing the privilege. Most 835 * work to connect to a device shou ld be done when the device is opened, 836 * and u ndone at the last close. The disconnect code needs to address 837 * concu rrency issu es with respect to open() and close() methods, as 838 * well as forcing all pending I/O requ ests to complete (by u nlinking 839 * them as necessary, and blocking u ntil the u nlinks complete). 840 */ 841 stru ct usb_driver {842 const char *name ;843 844 int (*probe ) (stru ct u sb_interface *intf ,845 const stru ct u sb_device_id *id );846 847 void (*disconnect ) (stru ct u sb_interface *intf );848 849 int (*u nlocked_ioctl) (stru ct u sb_interface *intf , u nsigned int code ,850 void *bu f );851 852 int (*su spend ) (stru ct u sb_interface *intf , pm_message_t message );853 int (*resu me ) (stru ct u sb_interface *intf );854 int (*reset_resu me)(stru ct u sb_interface *intf );855 856 int (*pre_reset )(stru ct u sb_interface *intf );857 int (*post_reset)(stru ct u sb_interface *intf );858 859 const stru ct u sb_device_id *id_table ;860 861 stru ct u sb_dynids dynids;862 stru ct u sbdrv_wrap drvwrap;863 u nsigned int no_dynamic_id:1;864 u nsigned int su pports_au tosu spend:1;865 u nsigned int soft_u nbind:1;866 };
usb_driver中的probe函数扫描连接到主机上的usb设备,并且注册usb接口驱动。
disconnect函数是当usb设备移除时调用。
/* 310 * Allocated per bu s (tree of devices) we have: 311 */ 312 stru ct u sb_bu s {313 stru ct device *controller ; /* host/master side hardware */ 314 int bu snu m; /* Bu s nu mber (in order of reg) */ 315 const char *bu s_name; /* stable id (PCI slot_name etc) */ 316 u 8 u ses_dma; /* Does the host controller u se DMA? */ 317 u 8 u ses_pio_for_control; /* 318 * Does the host controller u se PIO 319 * for control transfers? 320 */ 321 u 8 otg_port; /* 0, or nu mber of OTG/HNP port */ 322 u nsigned is_b_host:1; /* tru e du ring some HNP roleswitches */ 323 u nsigned b_hnp_enable:1; /* OTG: did A-Host enable HNP? */ 324 u nsigned sg_tablesize ; /* 0 or largest nu mber of sg list entries */ 325 326 int devnu m_next; /* Next open device nu mber in 327 * rou nd-robin allocation */ 328 329 stru ct u sb_devmap devmap; /* device address allocation map */ 330 stru ct usb_device * root_hu b; /* Root hu b */ 331 stru ct u sb_bu s *hs_companion; /* Companion EHCI bu s, if any */ 332 stru ct list_head bu s_list; /* list of bu sses */ 333 334 int bandwidth_allocated; /* on this bu s: how mu ch of the time 335 * reserved for periodic (intr/iso) 336 * requ ests is u sed, on average? 337 * U nits: microseconds/frame. 338 * Limits: Fu ll/low speed reserve 90%, 339 * while high speed reserves 80%. 340 */ 341 int bandwidth_int_reqs; /* nu mber of Interru pt requ ests */ 342 int bandwidth_isoc_reqs; /* nu mber of Isoc. requ ests */ 343 344 #ifdef CONFIG_USB_DEVICE FS345 stru ct dentry *u sbfs_dentry; /* u sbfs dentry entry for the bu s */ 346 #endif347 348 #if defined (CONFIG_U SB_MON) || defined (CONFIG_U SB_MON_MODU LE)349 stru ct mon_bu s *mon_bu s ; /* non-nu ll when associated */ 350 int monitored; /* non-zero when monitored */ 351 #endif352 };353
** 370 * stru ct usb_device - kernel's representation of a U SB device 371 * @devnu m: device nu mber; address on a U SB bu s 372 * @devpath: device ID string for u se in messages (e.g., /port/...) 373 * @rou te: tree topology hex string for u se with xHCI 374 * @state: device state: configu red, not attached, etc. 375 * @speed: device speed: high/fu ll/low (or error) 376 * @tt: Transaction Translator info; u sed with low/fu ll speed dev, highspeed hu b 377 * @ttport: device port on that tt hu b 378 * @toggle: one bit for each endpoint, with ([0] = IN, [1] = OU T) endpoints 379 * @parent: ou r hu b, u nless we're the root 380 * @bu s: bu s we're part of 381 * @ep0: endpoint 0 data (defau lt control pipe) 382 * @dev: generic device interface 383 * @descriptor: U SB device descriptor 384 * @config: all of the device's configs 385 * @actconfig: the active configu ration 386 * @ep_in: array of IN endpoints 387 * @ep_ou t: array of OU T endpoints 388 * @rawdescriptors: raw descriptors for each config 389 * @bu s_mA: Cu rrent available from the bu s 390 * @portnu m: parent port nu mber (origin 1) 391 * @level: nu mber of U SB hu b ancestors 392 * @can_su bmit: U RBs may be su bmitted 393 * @persist_enabled: U SB_PERSIST enabled for this device 394 * @have_langid: whether string_langid is valid 395 * @au thorized: policy has said we can u se it; 396 * (u ser space) policy determines if we au thorize this device to be 397 * u sed or not. By defau lt, wired U SB devices are au thorized. 398 * WU SB devices are not, u ntil we au thorize them from u ser space. 399 * FIXME -- complete doc 400 * @au thenticated: Crypto au thentication passed 401 * @wu sb: device is Wireless U SB 402 * @string_langid: langu age ID for strings 403 * @produ ct: iProdu ct string, if present (static) 404 * @manu factu rer: iManu factu rer string, if present (static) 405 * @serial: iSerialNu mber string, if present (static) 406 * @filelist: u sbfs files that are open to this device 407 * @u sb_classdev: U SB class device that was created for u sbfs device 408 * access from u serspace 409 * @u sbfs_dentry: u sbfs dentry entry for the device 410 * @maxchild: nu mber of ports if hu b 411 * @children: child devices - U SB devices that are attached to this hu b 412 * @qu irks: qu irks of the whole device 413 * @u rbnu m: nu mber of U RBs su bmitted for the whole device 414 * @active_du ration: total time device is not su spended 415 * @connect_time: time device was first connected 416 * @do_remote_wakeu p: remote wakeu p shou ld be enabled 417 * @reset_resu me: needs reset instead of resu me 418 * @wu sb_dev: if this is a Wireless U SB device, link to the WU SB 419 * specific data for the device. 420 * @slot_id: Slot ID assigned by xHCI 421 * 422 * Notes: 423 * U sbcore drivers shou ld not set u sbdev->state directly. Instead u se 424 * u sb_set_device_state(). 425 */ 426 stru ct usb_device {427 int devnu m;428 char devpath[16];429 u 32 rou te;430 enu m usb_device _state state ;431 enu m usb_device _speed speed ;432 433 stru ct u sb_tt *tt;434 int ttport;435 436 u nsigned int toggle [2];437 438 stru ct usb_device *parent ;439 stru ct u sb_bu s *bu s ;440 stru ct u sb_host_endpoint ep0;441 442 stru ct device dev ;443 444 stru ct usb_device _descriptor descriptor ;445 stru ct u sb_host_config *config ;446 447 stru ct u sb_host_config *actconfig;448 stru ct u sb_host_endpoint *ep_in[16];449 stru ct u sb_host_endpoint *ep_ou t[16];450 451 char **rawdescriptors;452 453 u nsigned short bu s_mA;454 u 8 portnu m;455 u 8 level;456 457 u nsigned can_su bmit:1;458 u nsigned persist_enabled:1;459 u nsigned have_langid:1;460 u nsigned au thorized:1;461 u nsigned au thenticated:1;462 u nsigned wu sb:1;463 int string_langid;464 465 /* static strings from the device */ 466 char *produ ct ;467 char *manu factu rer ;468 char *serial ;469 470 stru ct list_head filelist;471 #ifdef CONFIG_USB_DEVICE _CLASS472 stru ct device *u sb_classdev;473 #endif474 #ifdef CONFIG_USB_DEVICE FS475 stru ct dentry *u sbfs_dentry;476 #endif477 478 int maxchild;479 stru ct usb_device *children[U SB_MAXCHILDREN ];480 481 u 32 qu irks ;482 atomic_t u rbnu m;483 484 u nsigned long active_du ration;485 486 #ifdef CONFIG_PM 487 u nsigned long connect_time;488 489 u nsigned do_remote_wakeu p:1;490 u nsigned reset_resu me:1;491 #endif492 stru ct wu sb_dev *wu sb_dev ;493 int slot_id;494 };495 #define to_usb_device (d ) container_of (d , stru ct usb_device , dev )496 497 static inline stru ct usb_device *interface_to_u sbdev (stru ct u sb_interface *intf )498 {499 retu rn to_usb_device (intf ->dev .parent );500 }501
以上三个结构体分别是usb_driver,usb_bus,usb_device设备结构体。
usb_interface结构体:
struct usb_interface {160 /* array of alternate settings for this interface, 161 * stored in no particular order */ 162 struct usb_host_interface *altsetting ;163 164 struct usb_host_interface *cur_altsetting; /* the currently 165 * active alternate setting */ 166 unsigned num_altsetting; /* number of alternate settings */ 167 168 /* If there is an interface association descriptor then it will list 169 * the associated interfaces */ 170 struct usb_interface_assoc_descriptor *intf_assoc;171 172 int minor ; /* minor number this interface is 173 * bound to */ 174 enum usb_interface_condition condition; /* state of binding */ 175 unsigned sysfs_files_created:1; /* the sysfs attributes exist */ 176 unsigned ep_devs_created:1; /* endpoint "devices" exist */ 177 unsigned unregistering:1; /* unregistration is in progress */ 178 unsigned needs_remote_wakeup:1; /* driver requires remote wakeup */ 179 unsigned needs_altsetting0:1; /* switch to altsetting 0 is pending */ 180 unsigned needs_binding:1; /* needs delayed unbind/rebind */ 181 unsigned reset_running:1;182 unsigned resetting_device:1; /* true: bandwidth alloc after reset */ 183 184 struct device dev ; /* interface specific device info */ 185 struct device *usb_dev ;186 atomic_t pm_usage_cnt; /* usage counter for autosuspend */ 187 struct work_struct reset_ws; /* for resets in atomic context */ 188 };
struct usb_host_interface *altsetting包含了usb interface的所有可选设置。
struct usb_host _interface *cur_altsetting是usb interface的当前可选设置。
下面看一个struct usb_host_interface
/* host-side wrapper for one interface setting's parsed descriptors */ 77 stru ct usb_host_interface {78 stru ct u sb_interface_descriptor desc ;79 80 /* array of desc.bNu mEndpoint endpoints associated with this 81 * interface setting. these will be in no particu lar order. 82 */ 83 stru ct u sb_host_endpoint *endpoint ;84 85 char *string ; /* iInterface string, if present */ 86 u nsigned char *extra; /* Extra descriptors */ 87 int extralen;88 };
其中struct usb_interface_descriptor即是usb接口描述符。
struct usb_host_endpoint代表的是设备端点。
可以在desc中改变接口包含的端点数。
接下来看一下usb_host_endpoint这个结构体:
/** 50 * stru ct usb_host_endpoint - host-side endpoint descriptor and qu eu e 51 * @desc: descriptor for this endpoint, wMaxPacketSize in native byteorder 52 * @ss_ep_comp: Su perSpeed companion descriptor for this endpoint 53 * @u rb_list: u rbs qu eu ed to this endpoint; maintained by u sbcore 54 * @hcpriv: for u se by HCD; typically holds hardware dma qu eu e head (QH) 55 * with one or more transfer descriptors (TDs) per u rb 56 * @ep_dev: ep_device for sysfs info 57 * @extra: descriptors following this endpoint in the configu ration 58 * @extralen: how many bytes of "extra" are valid 59 * @enabled: U RBs may be su bmitted to this endpoint 60 * 61 * U SB requ ests are always qu eu ed to a given endpoint, identified by a 62 * descriptor within an active interface in a given U SB configu ration. 63 */ 64 stru ct usb_host_endpoint {65 stru ct u sb_endpoint_descriptor desc ;66 stru ct u sb_ss_ep_comp_descriptor ss_ep_comp;67 stru ct list_head u rb_list ;68 void *hcpriv;69 stru ct ep_device *ep_dev; /* For sysfs info */ 70 71 u nsigned char *extra; /* Extra descriptors */ 72 int extralen;73 int enabled ;74 };
其中struct usb_endpoint_descriptor是端点描述符。
urb(usb reqeust block):
urb主要用于Linux host与设备进行数据传输.
urb的生命周期:
(1)由usb设备驱动创建
(2)分配到usb设备的指定端点
(3)由Usb设备驱动提交到usb core
(4)由Usb core提交到usb 主机控制器
(5)由Usb主机控制器控制设备进行数据传输
(6)当urb完成的时候,usb主机控制器驱动通知usb 设备驱动
/** 1006 * stru ct urb - U SB Requ est Block 1007 * @urb _list: For u se by cu rrent owner of the URB . 1008 * @anchor_list: membership in the list of an anchor 1009 * @anchor: to anchor URB s to a common mooring 1010 * @ep: Points to the endpoint's data stru ctu re. Will eventu ally 1011 * replace @pipe. 1012 * @pipe: Holds endpoint nu mber, direction, type, and more. 1013 * Create these valu es with the eight macros available; 1014 * u sb_{snd,rcv}TYPEpipe(dev,endpoint), where the TYPE is "ctrl" 1015 * (control), "bu lk", "int" (interru pt), or "iso" (isochronou s). 1016 * For example u sb_sndbu lkpipe() or u sb_rcvintpipe(). Endpoint 1017 * nu mbers range from zero to fifteen. Note that "in" endpoint two 1018 * is a different endpoint (and pipe) from "ou t" endpoint two. 1019 * The cu rrent configu ration controls the existence, type, and 1020 * maximu m packet size of any given endpoint. 1021 * @stream_id: the endpoint's stream ID for bu lk streams 1022 * @dev: Identifies the U SB device to perform the requ est. 1023 * @statu s: This is read in non-iso completion fu nctions to get the 1024 * statu s of the particu lar requ est. ISO requ ests only u se it 1025 * to tell whether the URB was u nlinked; detailed statu s for 1026 * each frame is in the fields of the iso_frame-desc. 1027 * @transfer_flags: A variety of flags may be u sed to affect how URB 1028 * su bmission, u nlinking, or operation are handled. Different 1029 * kinds of URB can u se different flags. 1030 * @transfer_bu ffer: This identifies the bu ffer to (or from) which the I/O 1031 * requ est will be performed u nless URB _NO_TRANSFER_DMA_MAP is set 1032 * (however, do not leave garbage in transfer_bu ffer even then). 1033 * This bu ffer mu st be su itable for DMA; allocate it with 1034 * kmalloc() or equ ivalent. For transfers to "in" endpoints, contents 1035 * of this bu ffer will be modified. This bu ffer is u sed for the data 1036 * stage of control transfers. 1037 * @transfer_dma: When transfer_flags inclu des URB _NO_TRANSFER_DMA_MAP, 1038 * the device driver is saying that it provided this DMA address, 1039 * which the host controller driver shou ld u se in preference to the 1040 * transfer_bu ffer. 1041 * @sg: scatter gather bu ffer list 1042 * @nu m_sgs: nu mber of entries in the sg list 1043 * @transfer_bu ffer_length: How big is transfer_bu ffer. The transfer may 1044 * be broken u p into chu nks according to the cu rrent maximu m packet 1045 * size for the endpoint, which is a fu nction of the configu ration 1046 * and is encoded in the pipe. When the length is zero, neither 1047 * transfer_bu ffer nor transfer_dma is u sed. 1048 * @actu al_length: This is read in non-iso completion fu nctions, and 1049 * it tells how many bytes (ou t of transfer_bu ffer_length) were 1050 * transferred. It will normally be the same as requ ested, u nless 1051 * either an error was reported or a short read was performed. 1052 * The URB _SHORT_NOT_OK transfer flag may be u sed to make su ch 1053 * short reads be reported as errors. 1054 * @setu p_packet: Only u sed for control transfers, this points to eight bytes 1055 * of setu p data. Control transfers always start by sending this data 1056 * to the device. Then transfer_bu ffer is read or written, if needed. 1057 * @setu p_dma: DMA pointer for the setu p packet. The caller mu st not u se 1058 * this field; setu p_packet mu st point to a valid bu ffer. 1059 * @start_frame: Retu rns the initial frame for isochronou s transfers. 1060 * @nu mber_of_packets: Lists the nu mber of ISO transfer bu ffers. 1061 * @interval: Specifies the polling interval for interru pt or isochronou s 1062 * transfers. The u nits are frames (milliseconds) for fu ll and low 1063 * speed devices, and microframes (1/8 millisecond) for highspeed 1064 * and Su perSpeed devices. 1065 * @error_cou nt: Retu rns the nu mber of ISO transfers that reported errors. 1066 * @context: For u se in completion fu nctions. This normally points to 1067 * requ est-specific driver context. 1068 * @complete: Completion handler. This URB is passed as the parameter to the 1069 * completion fu nction. The completion fu nction may then do what 1070 * it likes with the URB , inclu ding resu bmitting or freeing it. 1071 * @iso_frame_desc: U sed to provide arrays of ISO transfer bu ffers and to 1072 * collect the transfer statu s for each bu ffer. 1073 * 1074 * This stru ctu re identifies U SB transfer requ ests. URB s mu st be allocated by 1075 * calling u sb_alloc_urb () and freed with a call to u sb_free_urb (). 1076 * Initialization may be done u sing variou s u sb_fill_*_urb () fu nctions. URB s 1077 * are su bmitted u sing u sb_su bmit_urb (), and pending requ ests may be canceled 1078 * u sing u sb_u nlink_urb () or u sb_kill_urb (). 1079 * 1080 * Data Transfer Bu ffers: 1081 * 1082 * Normally drivers provide I/O bu ffers allocated with kmalloc() or otherwise 1083 * taken from the general page pool. That is provided by transfer_bu ffer 1084 * (control requ ests also u se setu p_packet), and host controller drivers 1085 * perform a dma mapping (and u nmapping) for each bu ffer transferred. Those 1086 * mapping operations can be expensive on some platforms (perhaps u sing a dma 1087 * bou nce bu ffer or talking to an IOMMU ), 1088 * althou gh they're cheap on commodity x86 and ppc hardware. 1089 * 1090 * Alternatively, drivers may pass the URB _NO_TRANSFER_DMA_MAP transfer flag, 1091 * which tells the host controller driver that no su ch mapping is needed for 1092 * the transfer_bu ffer since 1093 * the device driver is DMA-aware. For example, a device driver might 1094 * allocate a DMA bu ffer with u sb_alloc_coherent() or call u sb_bu ffer_map(). 1095 * When this transfer flag is provided, host controller drivers will 1096 * attempt to u se the dma address fou nd in the transfer_dma 1097 * field rather than determining a dma address themselves. 1098 * 1099 * Note that transfer_bu ffer mu st still be set if the controller 1100 * does not su pport DMA (as indicated by bu s.u ses_dma) and when talking 1101 * to root hu b. If you have to trasfer between highmem zone and the device 1102 * on su ch controller, create a bou nce bu ffer or bail ou t with an error. 1103 * If transfer_bu ffer cannot be set (is in highmem) and the controller is DMA 1104 * capable, assign NU LL to it, so that u sbmon knows not to u se the valu e. 1105 * The setu p_packet mu st always be set, so it cannot be located in highmem. 1106 * 1107 * Initialization: 1108 * 1109 * All URB s su bmitted mu st initialize the dev, pipe, transfer_flags (may be 1110 * zero), and complete fields. All URB s mu st also initialize 1111 * transfer_bu ffer and transfer_bu ffer_length. They may provide the 1112 * URB _SHORT_NOT_OK transfer flag, indicating that short reads are 1113 * to be treated as errors; that flag is invalid for write requ ests. 1114 * 1115 * Bu lk URB s may 1116 * u se the URB _ZERO_PACKET transfer flag, indicating that bu lk OU T transfers 1117 * shou ld always terminate with a short packet, even if it means adding an 1118 * extra zero length packet. 1119 * 1120 * Control URB s mu st provide a valid pointer in the setu p_packet field. 1121 * U nlike the transfer_bu ffer, the setu p_packet may not be mapped for DMA 1122 * beforehand. 1123 * 1124 * Interru pt URB s mu st provide an interval, saying how often (in milliseconds 1125 * or, for highspeed devices, 125 microsecond u nits) 1126 * to poll for transfers. After the URB has been su bmitted, the interval 1127 * field reflects how the transfer was actu ally schedu led. 1128 * The polling interval may be more frequ ent than requ ested. 1129 * For example, some controllers have a maximu m interval of 32 milliseconds, 1130 * while others su pport intervals of u p to 1024 milliseconds. 1131 * Isochronou s URB s also have transfer intervals. (Note that for isochronou s 1132 * endpoints, as well as high speed interru pt endpoints, the encoding of 1133 * the transfer interval in the endpoint descriptor is logarithmic. 1134 * Device drivers mu st convert that valu e to linear u nits themselves.) 1135 * 1136 * Isochronou s URB s normally u se the URB _ISO_ASAP transfer flag, telling 1137 * the host controller to schedu le the transfer as soon as bandwidth 1138 * u tilization allows, and then set start_frame to reflect the actu al frame 1139 * selected du ring su bmission. Otherwise drivers mu st specify the start_frame 1140 * and handle the case where the transfer can't begin then. However, drivers 1141 * won't know how bandwidth is cu rrently allocated, and while they can 1142 * find the cu rrent frame u sing u sb_get_cu rrent_frame_nu mber () they can't 1143 * know the range for that frame nu mber. (Ranges for frame cou nter valu es 1144 * are HC-specific, and can go from 256 to 65536 frames from "now".) 1145 * 1146 * Isochronou s URB s have a different data transfer model, in part becau se 1147 * the qu ality of service is only "best effort". Callers provide specially 1148 * allocated URB s, with nu mber_of_packets worth of iso_frame_desc stru ctu res 1149 * at the end. Each su ch packet is an individu al ISO transfer. Isochronou s 1150 * URB s are normally qu eu ed, su bmitted by drivers to arrange that 1151 * transfers are at least dou ble bu ffered, and then explicitly resu bmitted 1152 * in completion handlers, so 1153 * that data (su ch as au dio or video) streams at as constant a rate as the 1154 * host controller schedu ler can su pport. 1155 * 1156 * Completion Callbacks: 1157 * 1158 * The completion callback is made in_interru pt(), and one of the first 1159 * things that a completion handler shou ld do is check the statu s field. 1160 * The statu s field is provided for all URB s. It is u sed to report 1161 * u nlinked URB s, and statu s for all non-ISO transfers. It shou ld not 1162 * be examined before the URB is retu rned to the completion handler. 1163 * 1164 * The context field is normally u sed to link URB s back to the relevant 1165 * driver or requ est state. 1166 * 1167 * When the completion callback is invoked for non-isochronou s URB s, the 1168 * actu al_length field tells how many bytes were transferred. This field 1169 * is u pdated even when the URB terminated with an error or was u nlinked. 1170 * 1171 * ISO transfer statu s is reported in the statu s and actu al_length fields 1172 * of the iso_frame_desc array, and the nu mber of errors is reported in 1173 * error_cou nt. Completion callbacks for ISO transfers will normally 1174 * (re)su bmit URB s to ensu re a constant transfer rate. 1175 * 1176 * Note that even fields marked "pu blic" shou ld not be tou ched by the driver 1177 * when the urb is owned by the hcd, that is, since the call to 1178 * u sb_su bmit_urb () till the entry into the completion rou tine. 1179 */ 1180 stru ct urb {1181 /* private: u sb core and host controller only fields in the urb */ 1182 stru ct kref kref ; /* reference cou nt of the URB */ 1183 void *hcpriv; /* private data for host controller */ 1184 atomic_t u se_cou nt ; /* concu rrent su bmissions cou nter */ 1185 atomic_t reject; /* su bmissions will fail */ 1186 int u nlinked; /* u nlink error code */ 1187 1188 /* pu blic: docu mented fields in the urb that can be u sed by drivers */ 1189 stru ct list_head urb _list ; /* list head for u se by the urb 's 1190 * cu rrent owner */ 1191 stru ct list_head anchor_list; /* the URB may be anchored */ 1192 stru ct u sb_anchor *anchor;1193 stru ct u sb_device *dev ; /* (in) pointer to associated device */ 1194 stru ct u sb_host_endpoint *ep ; /* (internal) pointer to endpoint */ 1195 u nsigned int pipe ; /* (in) pipe information */ 1196 u nsigned int stream_id ; /* (in) stream ID */ 1197 int statu s ; /* (retu rn) non-ISO statu s */ 1198 u nsigned int transfer_flags; /* (in) URB _SHORT_NOT_OK | ...*/ 1199 void *transfer_bu ffer; /* (in) associated data bu ffer */ 1200 dma_addr_t transfer_dma; /* (in) dma addr for transfer_bu ffer */ 1201 stru ct scatterlist *sg; /* (in) scatter gather bu ffer list */ 1202 int nu m_sgs; /* (in) nu mber of entries in the sg list */ 1203 u 32 transfer_bu ffer_length; /* (in) data bu ffer length */ 1204 u 32 actu al_length; /* (retu rn) actu al transfer length */ 1205 u nsigned char *setu p_packet ; /* (in) setu p packet (control only) */ 1206 dma_addr_t setu p_dma ; /* (in) dma addr for setu p_packet */ 1207 int start_frame; /* (modify) start frame (ISO) */ 1208 int nu mber_of_packets; /* (in) nu mber of ISO packets */ 1209 int interval ; /* (modify) transfer interval 1210 * (INT/ISO) */ 1211 int error_cou nt ; /* (retu rn) nu mber of ISO errors */ 1212 void *context ; /* (in) context for completion */ 1213 u sb_complete_t complete ; /* (in) completion rou tine */ 1214 stru ct u sb_iso_packet_descriptor iso_frame_desc[0];1215 /* (in) ISO ONLY */ 1216 };1217 1218 /* ----------------------------------------------------------------------- */
6. Linux usb 驱动的相关操作函数
int usb_register(struct usb_driver *d);void usb_deregister(struct usb_driver *d);Functions used to register and unregister a USB driver from the USB core.
这两个函数主要用来注册usb driver与解注册usb driver.
struct usb_device *interface_to_usbdev(struct usb_interface *intf);Retrieves the controlling struct usb_device * out of a struct usb_interface *.
返回一个usb接口返回一个usb_device.
void usb_set_intfdata(struct usb_interface *intf, void *data);void *usb_get_intfdata(struct usb_interface *intf);Functions to set and get access to the private data pointer section within thestruct usb_interface.
设置private data和是返回private data.
int usb_register_dev(struct usb_interface *intf, struct usb_class_driver*class_driver);void usb_deregister_dev(struct usb_interface *intf, struct usb_class_driver*class_driver);Functions used to register and unregister a specific struct usb_interface * structurewith a struct usb_class_driver * structure.
注册usb接口驱动和解注册usb接口驱动,接口驱动也就是设备驱动。
struct urb *usb_alloc_urb(int iso_packets, int mem_flags);void usb_free_urb(struct urb *urb);Functions used to create and destroy a struct usb urb *.
分配和释放urb.
void usb_fill_int_urb(struct urb *urb, struct usb_device *dev, unsigned intpipe, void *transfer_buffer, int buffer_length, usb_complete_t complete,void *context, int interval);void usb_fill_bulk_urb(struct urb *urb, struct usb_device *dev, unsigned intpipe, void *transfer_buffer, int buffer_length, usb_complete_t complete,void *context);void usb_fill_control_urb(struct urb *urb, struct usb_device *dev, unsignedint pipe, unsigned char *setup_packet, void *transfer_buffer, intbuffer_ length, usb_complete_t complete, void *context);Functions used to initialize a struct urb before it is submitted to the USB core.
这三个函数是用来初始化urb.
参数:
struct urb* urb 要初始化的urb结构体。
struct usb_device *dev urb发送到的设备
unsigned int pipe usb_sndintpipe和usb_rcvintpipe分别是usb发送端点管道和接收端点管道
void *transfer_buffer 接收或发送数据的缓冲区
int buffer_length 缓冲区的长度
usb_complete_t urb完成时的回调函数
int usb_bulk_msg(struct usb_device *usb_dev, unsigned int pipe, void *data,int len, int *actual_length, int timeout);int usb_control_msg(struct usb_device *dev, unsigned int pipe, __u8 request,__u8 requesttype, __u16 value, __u16 index, void *data, __u16 size,int timeout);Functions used to send or receive USB data without having to use a struct urb.
这两个函数的usb接收或发送数据没有使用urb结构体。
7. skelton程序
/* * USB Skeleton driver - 2.2 * * Copyright (C) 2001-2004 Greg Kroah-Hartman (greg@kroah.com) * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License as * published by the Free Software Foundation, version 2. * * This driver is based on the 2.6.3 version of drivers/usb/usb-skeleton.c * but has been rewritten to be easier to read and use. * */#include <linux/kernel.h>#include <linux/errno.h>#include <linux/init.h>#include <linux/slab.h>#include <linux/module.h>#include <linux/kref.h>#include <asm/uaccess.h>#include <linux/usb.h>#include <linux/mutex.h>/* Define these values to match your devices */#define USB_SKEL_VENDOR_ID 0xfff0#define USB_SKEL_PRODUCT_ID 0xfff0/* table of devices that work with this driver */static struct usb_device_id skel_table [] = { { USB_DEVICE(USB_SKEL_VENDOR_ID, USB_SKEL_PRODUCT_ID) }, { } /* Terminating entry */};MODULE_DEVICE_TABLE(usb, skel_table);/* Get a minor range for your devices from the usb maintainer */#define USB_SKEL_MINOR_BASE 192 //次设备号/* our private defines. if this grows any larger, use your own .h file */#define MAX_TRANSFER (PAGE_SIZE - 512)#define WRITES_IN_FLIGHT 8/* Structure to hold all of our device specific stuff */struct usb_skel { size_t udev; struct usb_device *dev; /* the usb device for this device */ struct usb_interface *interface; /* the interface for this device */ struct semaphore limit_sem; /* limiting the number of writes in progress */ unsigned char *bulk_in_buffer; /* the buffer to receive data */ size_t bulk_in_size; /* the size of the receive buffer */ __u8 bulk_in_endpointAddr; /* the address of the bulk in endpoint */ __u8 bulk_out_endpointAddr; /* the address of the bulk out endpoint */ struct kref kref; struct mutex io_mutex; /* synchronize I/O with disconnect */};#define to_skel_dev(d) container_of(d, struct usb_skel, kref)static struct usb_driver skel_driver;static void skel_delete(struct kref *kref){ struct usb_skel *dev = to_skel_dev(kref); usb_put_dev(dev->udev); kfree(dev->bulk_in_buffer); kfree(dev);}static int skel_open(struct inode *inode, struct file *file){ struct usb_skel *dev; struct usb_interface *interface; int subminor; int retval = 0; subminor = iminor(inode); interface = usb_find_interface(&skel_driver, subminor); if (!interface) { err ("%s - error, can't find device for minor %d", __FUNCTION__, subminor); retval = -ENODEV; goto exit; } dev = usb_get_intfdata(interface); if (!dev) { retval = -ENODEV; goto exit; } /* prevent the device from being autosuspended */ retval = usb_autopm_get_interface(interface); if (retval) goto exit; /* increment our usage count for the device */ kref_get(&dev->kref); /* save our object in the file's private structure */ file->private_data = dev;exit: return retval;}static int skel_release(struct inode *inode, struct file *file){ struct usb_skel *dev; dev = (struct usb_skel *)file->private_data; if (dev == NULL) return -ENODEV; /* allow the device to be autosuspended */ mutex_lock(&dev->io_mutex); if (dev->interface) usb_autopm_put_interface(dev->interface); mutex_unlock(&dev->io_mutex); /* decrement the count on our device */ kref_put(&dev->kref, skel_delete); return 0;}static ssize_t skel_read(struct file *file, char *buffer, size_t count, loff_t *ppos){ struct usb_skel *dev; int retval; int bytes_read; dev = (struct usb_skel *)file->private_data; mutex_lock(&dev->io_mutex); if (!dev->interface) { /* disconnect() was called */ retval = -ENODEV; goto exit; } /* do a blocking bulk read to get data from the device */ //usb_bulk_msg没有使用urb retval = usb_bulk_msg(dev->udev, usb_rcvbulkpipe(dev->udev, dev->bulk_in_endpointAddr), dev->bulk_in_buffer, min(dev->bulk_in_size, count), &bytes_read, 10000); /* if the read was successful, copy the data to userspace */ if (!retval) { if (copy_to_user(buffer, dev->bulk_in_buffer, bytes_read)) //复制到用户空间 retval = -EFAULT; else retval = bytes_read; }exit: mutex_unlock(&dev->io_mutex); return retval;}static void skel_write_bulk_callback(struct urb *urb){ struct usb_skel *dev; dev = (struct usb_skel *)urb->context; /* sync/async unlink faults aren't errors */ if (urb->status && !(urb->status == -ENOENT || urb->status == -ECONNRESET || urb->status == -ESHUTDOWN)) { err("%s - nonzero write bulk status received: %d", __FUNCTION__, urb->status); } /* free up our allocated buffer */ usb_buffer_free(urb->dev, urb->transfer_buffer_length, urb->transfer_buffer, urb->transfer_dma); up(&dev->limit_sem);}
//首先创建一个urb和buffer,初始化urb,然后提交urb.static ssize_t skel_write(struct file *file, const char *user_buffer, size_t count, loff_t *ppos){
struct usb_skel *dev; int retval = 0; struct urb *urb = NULL; char *buf = NULL; size_t writesize = min(count, (size_t)MAX_TRANSFER); dev = (struct usb_skel *)file->private_data; /* verify that we actually have some data to write */ if (count == 0) goto exit; /* limit the number of URBs in flight to stop a user from using up all RAM */ if (down_interruptible(&dev->limit_sem)) { retval = -ERESTARTSYS; goto exit; } mutex_lock(&dev->io_mutex); if (!dev->interface) { /* disconnect() was called */ retval = -ENODEV; goto error; } /* create a urb, and a buffer for it, and copy the data to the urb */ urb = usb_alloc_urb(0, GFP_KERNEL); if (!urb) { retval = -ENOMEM; goto error; } buf = usb_buffer_alloc(dev->udev, writesize, GFP_KERNEL, &urb->transfer_dma); if (!buf) { retval = -ENOMEM; goto error; } if (copy_from_user(buf, user_buffer, writesize)) { retval = -EFAULT; goto error; } /* initialize the urb properly */ usb_fill_bulk_urb(urb, dev->udev, usb_sndbulkpipe(dev->udev, dev->bulk_out_endpointAddr), buf, writesize, skel_write_bulk_callback, dev); urb->transfer_flags |= URB_NO_TRANSFER_DMA_MAP; /* send the data out the bulk port */ retval = usb_submit_urb(urb, GFP_KERNEL); if (retval) { err("%s - failed submitting write urb, error %d", __FUNCTION__, retval); goto error; } /* release our reference to this urb, the USB core will eventually free it entirely */ usb_free_urb(urb); mutex_unlock(&dev->io_mutex); return writesize;error: if (urb) { usb_buffer_free(dev->udev, writesize, buf, urb->transfer_dma); usb_free_urb(urb); } mutex_unlock(&dev->io_mutex); up(&dev->limit_sem);exit: return retval;}static const struct file_operations skel_fops = { .owner = THIS_MODULE, .read = skel_read, .write = skel_write, .open = skel_open, .release = skel_release,};/* * usb class driver info in order to get a minor number from the usb core, * and to have the device registered with the driver core */static struct usb_class_driver skel_class = { .name = "skel%d", .fops = &skel_fops, .minor_base = USB_SKEL_MINOR_BASE,};static int skel_probe(struct usb_interface *interface, const struct usb_device_id *id){ struct usb_skel *dev; struct usb_host_interface *iface_desc; //usb_host_interface包含usb interface的所有设置 struct usb_endpoint_descriptor *endpoint; //这个结构体是usb端点描述符 size_t buffer_size; int i; int retval = -ENOMEM; /* allocate memory for our device state and initialize it */ dev = kzalloc(sizeof(*dev), GFP_KERNEL); if (!dev) { err("Out of memory"); goto error; } kref_init(&dev->kref); sema_init(&dev->limit_sem, WRITES_IN_FLIGHT); mutex_init(&dev->io_mutex); dev->udev = usb_get_dev(interface_to_usbdev(interface)); //增加使用计数 dev->interface = interface; /* set up the endpoint information */ /* use only the first bulk-in and bulk-out endpoints */ iface_desc = interface->cur_altsetting; for (i = 0; i < iface_desc->desc.bNumEndpoints; ++i) { endpoint = &iface_desc->endpoint[i].desc; if (!dev->bulk_in_endpointAddr && usb_endpoint_is_bulk_in(endpoint)) { /* we found a bulk in endpoint */ buffer_size = le16_to_cpu(endpoint->wMaxPacketSize); dev->bulk_in_size = buffer_size; dev->bulk_in_endpointAddr = endpoint->bEndpointAddress; dev->bulk_in_buffer = kmalloc(buffer_size, GFP_KERNEL); if (!dev->bulk_in_buffer) { err("Could not allocate bulk_in_buffer"); goto error; } } if (!dev->bulk_out_endpointAddr && usb_endpoint_is_bulk_out(endpoint)) { /* we found a bulk out endpoint */ dev->bulk_out_endpointAddr = endpoint->bEndpointAddress; } } if (!(dev->bulk_in_endpointAddr && dev->bulk_out_endpointAddr)) { err("Could not find both bulk-in and bulk-out endpoints"); goto error; } /* save our data pointer in this interface device */ usb_set_intfdata(interface, dev); /* we can register the device now, as it is ready */ retval = usb_register_dev(interface, &skel_class); //注册usb设备 if (retval) { /* something prevented us from registering this driver */ err("Not able to get a minor for this device."); usb_set_intfdata(interface, NULL); goto error; } /* let the user know what node this device is now attached to */ info("USB Skeleton device now attached to USBSkel-%d", interface->minor); return 0;error: if (dev) kref_put(&dev->kref, skel_delete); return retval;}static void skel_disconnect(struct usb_interface *interface){ struct usb_skel *dev; int minor = interface->minor; /* prevent skel_open() from racing skel_disconnect() */ lock_kernel(); dev = usb_get_intfdata(interface); usb_set_intfdata(interface, NULL); /* give back our minor */ usb_deregister_dev(interface, &skel_class); /* prevent more I/O from starting */ mutex_lock(&dev->io_mutex); dev->interface = NULL; mutex_unlock(&dev->io_mutex); unlock_kernel(); /* decrement our usage count */ kref_put(&dev->kref, skel_delete); info("USB Skeleton #%d now disconnected", minor);}static struct usb_driver skel_driver = { .name = "skeleton", .probe = skel_probe, .disconnect = skel_disconnect, .id_table = skel_table,};static int __init usb_skel_init(void){ int result; /* register this driver with the USB subsystem */ result = usb_register(&skel_driver); if (result) err("usb_register failed. Error number %d", result); return result;}static void __exit usb_skel_exit(void){ //向usb子系统注册这个驱动 /* deregister this driver with the USB subsystem */ usb_deregister(&skel_driver);}module_init(usb_skel_init);module_exit(usb_skel_exit);MODULE_LICENSE("GPL");
分析:
skeleton.c 在/driver/usb/ 目录下,它是一个骨架驱动程序。
skeleton首先向usb子系统中注册驱动,然后注册设备。通常所说的usb驱动是指usb接口驱动。即完成一定的功能,数据处理。面 usb driver通过扫描确定usb设备是否在本驱动的设备列表中,即一个usb driver可能对应多个usb设备,它是用来辨别usb设备的。当usb设备移除时,调用disconnect函数。usb driver用于识别usb interface driver.
最后记住,一个接口对应一个设备驱动,主机与设备之间的数据传输是通过端点来实现的。urb是设备与主机之间数据交换的中介。
关于usb 主机驱动就介绍到这里了。