usb驱动分析论文.docx

上传人:b****5 文档编号:3800827 上传时间:2022-11-25 格式:DOCX 页数:5 大小:31.31KB
下载 相关 举报
usb驱动分析论文.docx_第1页
第1页 / 共5页
usb驱动分析论文.docx_第2页
第2页 / 共5页
usb驱动分析论文.docx_第3页
第3页 / 共5页
usb驱动分析论文.docx_第4页
第4页 / 共5页
usb驱动分析论文.docx_第5页
第5页 / 共5页
亲,该文档总共5页,全部预览完了,如果喜欢就下载吧!
下载资源
资源描述

usb驱动分析论文.docx

《usb驱动分析论文.docx》由会员分享,可在线阅读,更多相关《usb驱动分析论文.docx(5页珍藏版)》请在冰豆网上搜索。

usb驱动分析论文.docx

usb驱动分析论文

Linux课程设计

院系:

信息工程学院

专业:

10电子信息工程

学号:

姓名:

指导教师:

 

一、引言

  USB即通用串行总线,是一种全新的双向同步传输的支持热插拔的数据传输总线,其目的是为了提供一种兼容不同速度的、可扩充的并且使用方便的外围设备接口,同时也是为了解决计算机接口的太多的弊端而设计的。

一个USB系统主要有三部分组成:

USB互连、USB主机、USB设备三部分组成的。

在编写USB设备驱动程序设计时,可以分为三部分编写:

主机端设备驱动程序、主机控制器驱动程序设计和设备端驱动程序三部分,我将重点介绍主机端驱动程序的设计。

  二、USB设备驱动程序的设计

  USB设备驱动程序的设计包括主机端设备驱动程序设计、主机控制器驱动程序设计和设备端驱动程序设计三部分组成。

主机端设备驱动程序就是通常说的设备驱动程序,它是主机环境中为用户应用程序提供一个访问USB外设的接口。

Linux为这部分驱动程序提供编程接口,驱动程序设计者只要按照需求编写驱动程序框架,通过调用操作系统提供的API接口函数可以完成对USB外设的特定访问。

  主机控制驱动主要是对USB主机控制器的驱动,在大多数PC环境下,主机控制器都是由操作系统提供。

嵌入式设备一般都没有USB主机控制器,只是工作在Slave模式下。

如果要使USB具有主机功能,那么设备中需要选用一个带主机控制器的USB接口控制芯片,同时自己还要有实现该主机控制器的驱动程序。

目前Linux内核中只提供USB主机控制器的开放主机控制器和通用主机控制器接口两种规格,而这两种规格主要用在PC架构中。

USB主机端驱动程序与主机控制器的结构如图2所示。

其中USB核是Linux的一个子模块,集中定义了一组USB相关的数据结构、宏以及API函数。

  USB设备驱动程序是常说的设备固件程序的一部分,提供设备信息与主机的通信接口。

设备端USB驱动程序设计由以下几部分处理程序组成。

初始化例程:

完成描述符指针、端点、配置改变等操作。

数据传输例程:

完成控制一、引言

准设备处理请求:

处理标准设备请求。

厂商请求处理:

处理生产商指定请求。

其他操作:

处理主机发出的端口复位、配置改变等操作。

  1.USB设备驱动程序框架

  USB驱动程序首先要向Linux内核注册自己,并告诉系统它所支持的设备类型以及它所支持的操作。

这些信息通过一个usb_driver结构来传递。

usb_driver结构如下:

  staticstructusb_driverskel_driver={

  name:

"skeleton";/*驱动程序的名称*/

  probe:

skel_probe;/*设备列举时被调用*/

  disconnect:

skel_disconnect;/*设备被卸载时被调用*/

  fops:

&skel_fops;/*指向一个file_operation结构,内核通过它来访问驱动程序的文件操作函数,与用户程序的read、write等操作进行交互*/

  minorUSB_SKEL_MINOR_BASE;/*指向设备的次设备号,用于系统识别主设备号相同的设备(即一个驱动程序可以同时支持多个USB设备*/

  id_table:

skel_table;/*保存设备的厂商ID和产品ID,作为该设备的唯一标识,驱动程序向系统注册后,当下次插入时,系统根据这个标识查找正确的驱动程序,实现设备的即插即用*/

  };

  staticstructfile_operationskel_fops={

  {

  owner:

THIS_MODULE,

  read:

skel_read,

  write:

skel_write,

 ioctl:

skel_ioctl,

  open:

skel_open,

  release:

skel_release,

  };

  

(1)注册和注销

  USB驱动程序注册,就是把在初始化函数中填好的use_driver结构作为参数传递给

  use_register()函数即可,函数的调用方法为:

  result=usb_register(&skel_driver);

  当要从系统卸载驱动程序时,也是将use_driver结构作为参数传递给usb_deregister函数处理。

函数的调用格式为:

  staticvoid__exitusb_skel_exit(void)

  {/*deregisterthisdriverwiththeUSBsubsystem*/

  usb_deregister(&skel_driver);

  }

  module_exit(usb_skel_exit);

  当USB设备插入时,为了使linux-hotplug(Linux中PCI、USB等设备热插拔支持)系统自动装载驱动程序,需要创建一个MODULE_DEVICE_TABLE。

核心代码如下(这个模块仅支持某一特定设备):

  /*tableofdevicesthatworkwiththisdriver*/

  staticstructusb_device_idskel_table[]={

  {USB_DEVICE(USB_SKEL_VENDOR_ID,

  USB_SKEL_PRODUCT_ID)},

  {}/*Terminatingentry*/

  };

  MODULE_DEVICE_TABLE(usb,skel_table);

  USB_DEVICE宏利用厂商ID和产品ID提供了一个设备的唯一标识。

当系统插入一个ID匹配的USB设备到USB总线时,驱动会在USBcore中注册,驱动程序中probe函数也就会被调用。

usb_device结构指针、接口号和接口ID都会被传递到函数中。

  

(2)probe()函数

  probe()函数的编写格式为:

staticvoid*skel_probe(structusb_device*dev,unsignedintifnum,conststructusb_device_id*id);驱动程序需要确认插入的设备是否可以被接受,如果不接受,或者在初始化的过程中发生任何错误,probe()函数返回一个NULL值。

否则返回一个含有设备驱动程序状态的指针,通过这个指针,就可以访问所有结构中的回调函数。

  在驱动程序里,最后一点是要注册devfs(设备文件系统)。

首先创建一个缓冲用来保存那些被发送给USB设备的数据和那些从设备上接受的数据,并为设备传输创建一个USB请求块(URB)以向设备写入数据,同时USBurb被初始化,然后在devfs子系统中注册设备,允许devfs用户访问USB的设备。

注册过程如下:

  /*initializethedevfsnodeforthisdeviceandregisterit*/

  sprintf(name,"skel%d",skel->minor);

  skel->devfs=devfs_register(usb_devfs_handle,name,DEVFS_FL_DEFAULT,USB_MAJOR,USB_SKEL_MINOR_BASE+skel->minor,S_IFCHR|S_IRUSR|S_IWUSR|S_IRGRP|S_IWGRP|S_IROTH,&skel_fops,NULL);

  如果devfs_register函数失败,devfs子系统会将此情况报告给用户。

如果设备从USB总线拔掉,设备指针会调用disconnect函数。

驱动程序就需要清除那些被分配了的所有私有数据、关闭urbs,并且从devfs上注销调自己。

调用函数的格式为:

  /*removeourdevfsnode*/

  devfs_unregister(skel->devfs);

  现在,skeleton驱动就已经和设备绑定上了,任何用户态程序要操作此设备都可以通过file_operations结构所定义的函数进行了。

  (3)open()、write()和read()函数

  首先,要打开此设备。

在open()函数中MODULE_INC_USE_COUNT宏是一个关键,它起到一个计数的作用,有一个用户态程序打开一个设备,计数器就加1。

例如,以模块方式加入一个驱动,若计数器不为零,就说明仍然有用户程序在使用此驱动,这时候,就不能通过rmmod命令卸载驱动模块了。

  /*incrementourusagecountforthemodule*/

  MOD_INC_USE_COUNT;

  ++skel->open_count;

  /*saveourobjectinthefile'sprivatestructure*/

  file->private_data=skel;

  当open完设备后,read()、write()函数就可以收、发数据了。

  read()函数首先从open()函数中保存的fi。

  Write()函数和read()函数是完成驱动对读写等操作的响应。

在skel_write中,一个FILL_BULK_URB函数,就完成了urb系统callbak和的skel_write_bulk_callback之间的联系。

注意skel_write_bulkcallback是中断方式,所以要注意时间不能太久,本程序中它就只是报告一些urb的状态等。

read函数与write函数稍有不同在于:

程序并没有用urb将数据从设备传送到驱动程序,而是用usb_bulk_msg函数代替,这个函数能够不需要创建urbs和操作urb函数的情况下,来发送数据给设备,或者从设备来接收数据。

调用usb_bulk_msg函数并传到一个存储空间,用来缓冲和放置驱动收到的数据,若没有收到数据表示失败并返回一个错误信息。

  usb_bulk_msg函数:

当对usb设备进行一次读或者写时,usb_bulk_msg函数是非常有用的;然而,当需要连续地对设备进行读/写时,应建立一个自己的urbs,同时将urbs提交给USB子系统。

  skel_disconnect函数:

当释放设备文件句柄时,这个函数会被调用。

  MOD_DEC_USE_COUNT宏也会被调用到(和MOD_INC_USE_COUNT刚好对应,它减少一个计数器),首先确认当前是否有其他的程序正在访问这个设备,如果是最后一个用户在使用,可以关闭任何正在发生的写,操作如下:

  /*decrementourusagecountforthedevice*/

  --skel->open_count;

  if(skel->open_count<=0){

  /*shutdownanybulkwritesthatmightbe

  goingon*/

  usb_unlink_urb(skel->write_urb);

  skel->open_count=0;

  }

  /*decrementourusagecountforthemodule*/

  MOD_DEC_USE_COUNT;

  USB设备可以在任何时间点从系统中取走,即使程序目前正在访问它。

USB驱动程序必须要能够很好地处理解决此问题,它需要能够切断任何当前的读写,同时通知用户空间程序:

USB设备已经被取走。

 

  三、结语 USB规范是一门比较新的技术,接口使用方便,但是驱动程序的设计较复杂。

上面介绍了USB设备驱动程序的设计,主要分析了主机端驱动程序的设计。

 

展开阅读全文
相关资源
猜你喜欢
相关搜索

当前位置:首页 > 小学教育 > 语文

copyright@ 2008-2022 冰豆网网站版权所有

经营许可证编号:鄂ICP备2022015515号-1