⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 全面接触usb技术.txt

📁 驱动开发过程中要注意的一些要点以及一些基本资料
💻 TXT
📖 第 1 页 / 共 5 页
字号:
1.3 Windows 2000和WDM 驱动程序的设计目标 
WDM设备驱动程序和Windows2000在设计目标上有很多方面是一致,尤其是系统输入输出管理器更是如此。这些目标包括以下几方面: 
A) 优秀的可移植性 
Windows2000用以下几种方法实现在不同的硬件结构和平台上的可移植性: 
大多数的Windows2000组件提供一组内核服务例程, 供驱动程序和其它内核组件调用。 这些服务例程提供统一的编程接口,尽管这些服务例程底层的实现因为Windows版本不同而不同,而他们的编程接口保持稳定不变,这就使得基于其上的组件和驱动程序保持平台无关性和向后兼容性。 
Windows2000采用了分层设计,依赖于处理机体系结构和平台的系统底层部分被隔离的单独模块之中,所以系统的高层可以被屏蔽在千差万别硬件平台之外。提供操作系统可移植性的两个关键组件是HAL和内核。依赖于体系结构的功能(如线程描述表的切换)在内核中实现。在相同体系结构中,与计算机硬件交互的功能在HAL中实现。 
Windows 2000主要是用可移植C语言编写--操作系统执行体、实用程序、设备驱动程序使用C语言编写,图形子系统部份和用户界面是用C++语言编写。只有那些必须和系统硬件通信的操作系统部分(如中断处理程序),和性能极度敏感(如描述表切换)的部分使用汇编语言编写。汇编语言代码不仅存在于内核及HAL之中,而且存在于执行体中的少量区域(例如实现执行体里本地过程调用机构中的一个模块),甚至存在在一些用户态代码库中。多数Windows2000组件是用C语言编写,所以这个操作系统就容易在复杂指令CPU平台和精简指令计算机CPU的平台上移植。内核设备驱动程序也应当用C语言编写,这样它也可以在系统兼容的编译器上重新编译链接直接生成不同平台的设备驱动程序。WDM驱动程序同时可以在Windows98以后的系列操作系统中保持兼容,而不用重新编写代码。 
为保证系统的可移植性,驱动程序应避免使用平台相关的C编译器进行编译。大体上讲,驱动程序的代码尽可能用标准C编写的.驱动程序应注意以下几点: 
1) 驱动程序代码应避免使用平台相关的数据结构 
2) 避免调用任何保持状态的C运行时库函数 
3) 应尽量使用操作系统提供的服务例程同时尽量少的使用C运行时库函数 
4) 不能在驱动程序中使用浮点运算 
B) 软硬件可配置性 
避免使用机器相关的硬编码,使得同一硬件可以在其它不同配置的机器上运行,这叫做硬件可配置性。 
底层的驱动程序要为上层的各种驱动程序服务,它不能武断地猜测上层驱动的性质和特定实现,这叫做软件可配置性。 
Windows 2000的配置管理器提供了注册登记(Registry)数据库,在其中存储了系统的硬件、各种外设及其驱动程序的信息。驱动程序可以从中得到机器的硬件配置和系统中的其它驱动信息。即插即用管理器和内核驱动程序利用注册数据库来取得本机上硬件以及其它驱动程序的配置。Win2000驱动程序也把自己的设备信息以及机器相关的配置信息储存于此。 
C) 总是可以被剥夺执行权,总是可以被中断 
在Windows2000中内核组件代码按照以下优先级原则进行运行: 
内核定义的线程优先级策略 
系统中各线程都有其自身的优先级属性。大体上讲儿,大多数系统线程都有可变的优先级属性,它们总是可以被剥夺的而且它们和其它优先级相同线程一起被调度。一些系统中的线程具有实时优先级,它们可以抢先其它低优先级线程运行,同时它们也被优先级更高的线程抢先。 
内核定义的中断请求级策略 
内核同时把不同的软件中断和硬件中断赋予不同的优先级,这样某些高优先级的内核代码就能够运行在较高的中断请求级,某些特定的实时代码就能拥有很高的调度优先权。通过内核代码中运行的中断请求级可以确定相应的硬件优先级。内核模式代码应该始终可以被中断,较高优先级的中断随时都有可能发生,它可以中断当前执行的代码,立即投入运行。换句话说,在一定中断请求级上运行的代码在当前处理器上可以屏蔽相同或较低优先级的中断。内核定义了一种可移植的IRQL,如果处理器具有特殊的中断相关的特性(例如,第二时钟),则可以增加IRQL。按优先级排队中断,较高优先级的中断可以抢先较低优先级的中断服务,每个处理器IRQL设置决定了处理机可以接受哪些中断,IRQL也被用于同步访问核心态数据结构,当核心态线程运行时,它可以降低或提高处理器的IRQL。如果中断源的IRQL高于当前中断设置,则它的中断可以中断处理器;如果中断源的IRQL等于或低于当前中断级,则它的中断将被封锁或屏蔽,直到一个正在执行的线程降低了IRQL。 
操作系统的可以被剥夺和可以被中断的设计目标带来的好处是最大限度提高平均性能,任何中断服务例程都可以被更高中断请求级的中断服务例程中断,任何线程都可以被更高优先级的线程抢先。 
D) 多处理器安全 
在Windows2000多CPU操作系统平台,以下几种情况有可能发生: 
在对称多处理多平台上,每个处理机都可以访问内存,发生中断,访问输入输出控制寄存器。(比较而言,在非对称多处理平台上,只有主CPU可以处理中断。) 
Windows2000被设计为可以不加修改地运行在单处理器和多处理器平台上,所有驱动程序也必须安全的实现多处理器安全,避免被一个处理机访问和修改的存储器同时被另一台处理器访问和改变,比如说,一个设备的中断同时在两个处理器上发生,那么在一个处理器上特定优先级上的中断服务例程必须提供某种机制排他的访问临界区。在多处理器情况下,驱动程序的输入和输出请求可能是重叠的,这就是说,一台处理机正在处理输入请求,而另一个处理器在和设备通信,在这种情况下,所有的驱动程序必须同步对共享的资源进行访问(如果有必要的话)。内核组件提供一种叫自旋锁的机制,用来在多处理机平台上保护共享数据,使用自旋锁有以下两条原则: 
在一个时刻只有一个例程能够获得此自旋锁,只有持有它的例程可以访问被自旋锁保护数据,其它例程必须等待这个例程是释放自旋锁,然后重新获得后,才能去接触共享的数据。 
每一个系统中的自旋锁都有相关的中断请求级,只有运行在这个中断请求级上的例程才有可能获得自旋锁。 
E) 基于面向对象的设计的思想 
Windows2000是基于面向对象的思想设计,执行体中的不同组件定义了许多对象类型,每一个组件同时提供了操纵这些对象方法,组件不允许直接操作其它组件的对象,为使用其它组件的对象,必须使用其提供的接口。严格遵循这些原则有利于增强Windows2000的可移植性和灵活性,例如,未来版本的Windows操作系统有可能部分或者全部的重新定义这些对象结构,这些被重写的对象版本将不会对现有的执行体组件产生影响,换句话说,操作系统中组件的通信服务方式也是基于接口,驱动程序同样应该避免使用引用或者指针操作对象本身。 
和操作系统一样,驱动程序和他们的设备也是基于面向对象对象设计的,对系统的其它组件而言(包括用户代码),同设备联系被定义为一种打开文件操作,在输入输出子系统中,每一个驱动程序(逻辑,虚拟,和物理设备)都?quot;设备对象"来表示,每一个驱动程序加载映像都用"驱动对象"表示。输入输出管理器定义这些对象。 
F) 依可重用的包(输入输出请求包,IRP,I/O Request Packet)驱动的I/O 
输入输出管理器的主要任务是接收输出请求(通常来自于用户应用程序),创建IRP来代表它,将这些IRP引导到正确的服务例程来处理;并且跟踪他们直到他们被完成,最后向发起者返回状态参数。输入输出管理器,插即用管理器,电源管理器使用IRP来同核心态驱动程序进行通信,并且允许驱动程序之间进行通信。因此每一个IRP都由两大部成: 
固定部分:输出输入管理器用来保持原始输入请求信息,例如调用者线程ID和调用参数,打开文件指定的设备对象,等等。固定部分同时包含一个输入输出状态,驱动程序用于返回输入输出操作的结果。 
可变部分:数量不同的输入输出堆栈,用于支持分层的驱动程序结构。 
G) 支持异步I/O 
I/O管理器提供异步I/O支持以便I/O传输的发起者可以不必等待I/O操作的完成而继续它的工作。异步I/O提高了用户应用的性能,也提高了驱动程序的性能。异步I/O使得驱动程序不必按照I/O请求到来的顺序进行操作。这样,驱动程序内部必须维护I/O请求当前处理的阶段状态。 
w 内核驱动程序处理I/O请求的次序不一定和这些I/O请求到达I/O管理器的次序相同。I/O管理器或高层驱动也可以将大的数据请求块划分为多个小块来进行处理。而且,内核驱动并不一定串行的处理这些I/O请求。这就是说,驱动程序不一定等到前一个IRP完成才去处理下一个IRP。 


2. WDM驱动程序和I/O子系统的协同工作机制分析 
  在Windows驱动程序模型(WDM)出现之前Microsoft为它的两个系列操作系统提供了不同的驱动程序模型,他们分别是:Windows3.1和Windows95的Vxd以及NT式的驱动程序。两种驱动程序的架构是如此的不同,以至于程序员必须为每个设备在两种系统上分别编写、编译、调试驱动代码,这对于程序员来说是一个很大的负担。 
为统一驱动程序架构,减轻程序员的负担,微软推出了新型的WDM驱动程序模型,现在的Windows 98(第二版)以及Windows 2000均采用了这个模型。而且微软已经宣布未来的Windows系列操作系统的驱动模型将是基于WDM构架的。 
Windows驱动程序模型(WDM)的设计思想是非常先进的,它迎合了当前的高级操作系统的设计的先进之处: 
它是支持多处理器架构的,完全支持对称多处理 
它是处理器无关的,支持多种处理器架构。 
它完全支持即插即用和电源管理 
尽管对于用户来说Windows 98 and Windows 2000下的模型是相同的,但是他们的工作机制是完全不同的,以下将分别讨论。

2.1 Windows2000下的WDM驱动程序和I/O子系统的协同工作机制分析 

Windows 2000是分态的操作系统,因此在系统中代码运行在两种模式下:用户态和核心态。用户应用程序运行在用户态,操作系统代码(如系统服务和设备驱动程序)在核心态下运行。在核心态处理器模式中,代码可以访问所有系统内存和所有的CPU指令。操作系统软件的特权级别高于应用程序软件,通过这种机制,使得应用程序的不当行为在总体上不会破坏系统的稳定性。Windows 2000对核心态运行的组件不提供任何保护。换句话说,一旦处于核心态,系统代码就可以完全访问系统内存空间,并在访问时不受安全性的约束。 
Win32 应用程序运行在用户态,操作系统严格限制应用程序的行为,防止其对其它应用和系统代码的破坏。因此用户态程序只能调用Win32子系统提供的API来同设备交互,Win32子系统模块中的服务代码然后调用平台无关的系统服务例程来切入核心态并调用核心态组件(I/O管理器)提供的服务例程。当请求传递到I/O管理器时,它创建一个IRP(I/O Request Packet)并将其传递到适当的驱动程序去,并给应用程序一个消息,通知这次I/O操作还没完成。应用程序收到通知后或者继续执行,或者挂起等待。在任何一种情况下驱动程序独立的执行来服务应用程序。 
驱动程序最终需要访问硬件来完成I/O请求,在程序控制的I/O方式下的读请求,驱动程序的动作为读I/O端口或寄存器。尽管驱动程序运行在核心态下,可以直接和硬件交互,但在大多数情况下,为保持其可移植性,驱动程序一般调用硬件抽象层提供的例程来和硬件交互。硬件抽象层提供一种与处理器平台无关的方法来执行实际的I/O 操作。例如,在Intel x86处理器平台上,硬件抽象层使用IN指令,在Alpha平台上,它将使用MEMORY读取操作。 
驱动程序完成I/O操作后,它将调用一个特殊的内核服务例程来完成IRP。这时,因这个I/O请求挂起的任何Win32应用将继续执行。 

2.2 Windows 98下的WDM驱动程序和I/O子系统的协同工作机制分析 
  在Windows98中,操作系统内核被称为虚拟机管理器(VMM),因为它的主要任务是在单一的物理硬件上创建一个或多个"虚拟"的机器来共享这些硬件。而虚拟设备驱动程序(VxD)的设计初衷也是虚拟一个特定的硬件来辅助虚拟机管理器产生一种假象,那就是:每一个虚拟机都拥有一套完整的硬件。这种设计源于Windows 3.0,并在Windows 95和Windows 98中沿用。 
  Windows98并不象Windows 2000那样统一有序的处理I/O请求。Windows98在处理磁盘、串口、键盘等等这些不同的设备时采用的机制有很大不同。并且如图3所示,Windows98在处理32位和16位应用的I/O请求时,采用的方法也是根本不同的。图3中的左列展示了系统是如何处理32位应用的I/O请求的。在Windows98中,对于不同的设备,应用程序采用不同的机制来和驱动程序进行交互。应用程序可能调用一个Win32 API例如ReadFile来读设备,但这些设备仅包括磁盘文件,串口,和一些由WDM驱动程序驱动的设备。但对于其它设备,应用程序只能通过基于DeviceIoControl的一些特别的机制来和设备通讯。即使是同样调用ReadFile,应用程序使用一种机制来和磁盘驱动交互,采用另一种机制和串口驱动通讯。而由WDM驱动的设备的I/O请求方法和前两种又有本质的不同。 
图3的中列和右列展示了系统是如何处理16位(Windows 3.1)和DOS应用程序的I/O请求的。在两种情况下,应用程序都直接或间接的和用户态驱动程序进行交互,用户态驱动程序将请求传递到核心态虚拟设备驱动,再由核心态虚拟设备驱动代理应用程序和硬件直接交互。 
虽然在Windows 2000中以一种统一的方式(IRP)在内核中传递I/O操作,但在Windows 98中,即使在核心态也没有统一方法的来代表I/O请求。 
但对于WDM驱动程序来说,Windows 98在处理方式上通过一个系统模块(NTKERN.VXD)来模仿Windwos 2000内核的处理方法。这个模块提供了Windows 2000内核的大部分服务例程的仿真,并模拟I/O管理器来产生和发送IRP。WDM驱动程序几乎无法区分两种平台的差异。 


3 分层的设备驱动程序和即插即用设备栈 
3.1 分层的设备驱动程序 
  用户的动作最后如何由设备驱动程序处理。应用程序对设备I/O进行Win32调用,这个调用由I/O系统接收。I/O 管理器发送IRP来请求驱动程序的处理。 
在最简单的情况下,I/O管理器只是把IRP传递给一个设备驱动程序,这个设备驱动程序和硬件交互,并完成IRP的处理。I/O管理器把数据和结果返回给Win32和用户应用程序。 
通常IRP由分层的驱动程序栈来处理。高层的驱动程序把请求划分成更简单的请求并传递给下层驱动程序。例如,在文件系统驱动程序中,最高层的驱动程序知道文件如何在磁盘上表示,但不知道如何得到数据的细节。中间层次的驱动程序进一步处理请求,将一个IRP中的请求划分为若干个小的请求并传给下层驱动程序。最后,最低层的驱动程序与硬件打交道。 
在任何地的地方,驱动程序被设计为尽可能的通用。例如,SCSI端口知道如何把磁盘数据请求转换成SCSI请求,但是,它再向SCSI小端口驱动程序发出SCSI请求,这些小端口驱动程序知道如何访问各种SCSI硬件。 
过滤驱动程序是一种中间驱动程序,它位于其它的驱动程序层次之间,提供一些附加的功能,而不影响其它驱动程序。例如,过滤驱动程序可以用以提供容错的磁盘访问,在这个驱动程序中,数据被写到两个不同的物理磁盘,保证数据的冗余保存。 

3.2 即插即用设备栈 
Windows驱动程序模型重新定义驱动程序分层,以适用于即插即用系统。一个设备栈代表处理请求的驱动程序层次,总线驱动程序控制对总线上的所有设备的访问。例如,如果访问USB设备,必须使用USB总线驱动程序。 
总线驱动程序负责枚举它的总线,这意味着发现总线上的全部设备和检测设备何时被添加或删除。总线驱动程序创建一个物理设备对象来代表它发现的设备。一些总线驱动程序简单的控制对总线的访问,一旦有了控制权,就可以对总线做任何想要的工作。在其它情况下,总线驱动程序为我们处理总线上的所有事务。 
功能驱动程序知道如何控制设备的主要功能,它分层在总线驱动程序的上面。功能驱动程序创建一个功能设备对象,放在设备栈中,在USB的情况下,功能驱动程序必须使用USB类驱动程序访问它的设备。但是,在其余情况下,一旦总线驱动程序接管,功能驱动程序可以直接访问硬件。有多个功能驱动程序分层在第一个功能驱动程序之上是非常可能的。 
各种类型的过滤驱动程序可以插在设备栈中。对总线上的所有设备,总线过滤驱动程序被加在总线驱动程序之上;而对于特定类的所有功能驱动程序,添加类过滤驱动程序。设备过滤驱动程序仅对特定的设备添加。上层的过滤驱动程序在功能驱动程序之上,而底层过滤驱动程序在功能驱动程序之下。 
用户的请求总是在设备栈的顶部进入。假设用户程序标志了一个它想访问的功能设备,I/O管理器保证它的全部请求都发送到设备栈的顶部,这样任何高层的过滤驱动程序或功能驱动程序首先得到处理这些请求的机会。 

3.3 标准总线驱动程序和类驱动程序 
Windows提供的主要类驱动程序和总线驱动程序,是作为总线驱动程序和功能驱动程序执行的通用驱

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -