<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="zh">
	<id>https://arolstar52-zhtest.hf.space/index.php?action=history&amp;feed=atom&amp;title=Windows_Driver_Model</id>
	<title>Windows Driver Model - 版本历史</title>
	<link rel="self" type="application/atom+xml" href="https://arolstar52-zhtest.hf.space/index.php?action=history&amp;feed=atom&amp;title=Windows_Driver_Model"/>
	<link rel="alternate" type="text/html" href="https://arolstar52-zhtest.hf.space/index.php?title=Windows_Driver_Model&amp;action=history"/>
	<updated>2026-06-26T09:55:27Z</updated>
	<subtitle>在这个wiki上该页的修订历史</subtitle>
	<generator>MediaWiki 1.43.8</generator>
	<entry>
		<id>https://arolstar52-zhtest.hf.space/index.php?title=Windows_Driver_Model&amp;diff=176377&amp;oldid=prev</id>
		<title>~2025-33547-29 来自 2025年11月14日 (五) 12:09</title>
		<link rel="alternate" type="text/html" href="https://arolstar52-zhtest.hf.space/index.php?title=Windows_Driver_Model&amp;diff=176377&amp;oldid=prev"/>
		<updated>2025-11-14T12:09:26Z</updated>

		<summary type="html">&lt;p&gt;&lt;/p&gt;
&lt;p&gt;&lt;b&gt;新页面&lt;/b&gt;&lt;/p&gt;&lt;div&gt;{{noteTA&lt;br /&gt;
|G1=IT&lt;br /&gt;
|1=zh-tw:核心;zh-hk:內核;zh-cn:内核;&lt;br /&gt;
}}&lt;br /&gt;
&amp;#039;&amp;#039;&amp;#039;Windows驅動程式模型&amp;#039;&amp;#039;&amp;#039;（&amp;#039;&amp;#039;&amp;#039;Windows Driver Model&amp;#039;&amp;#039;&amp;#039;，簡稱WDM），是[[微軟]][[Windows作業系統]]的[[驅動程式]]設計架構，包括對於各項裝置（Device）的支援，如鍵盤（Keyboard）、滑鼠（Mouse）、網路卡（Network Driver Interface Specification，Ndis）、通用序列匯流排（Universal Serial Bus，USB）等。WDM可支援Windows 98, Windows 98 Second Edition, Windows Me, Windows 2000, Windows XP以及Windows Server 2003在x86平台上的建制工作。這個架構分成好幾個管理層面：&lt;br /&gt;
&lt;br /&gt;
*核心（Kernel）&lt;br /&gt;
*物件管理（Object Manager）&lt;br /&gt;
*執行（Executive）&lt;br /&gt;
*輸入輸出管理（I/O Manager）&lt;br /&gt;
*記憶體管理（Memory Manager）&lt;br /&gt;
*行程服務（Process Service）&lt;br /&gt;
*執行時期函式庫（Run-time Library）&lt;br /&gt;
*電源管理（Power Manager）&lt;br /&gt;
*隨插即用子系統（Plug and Play Subsystem）&lt;br /&gt;
*視窗管理指令（Windows Management Instrumentation，WMI）&lt;br /&gt;
*核心流（Kernel Streaming）&lt;br /&gt;
*硬體抽象層（Hardware Abstraction Layer）&lt;br /&gt;
&lt;br /&gt;
== 種類 ==&lt;br /&gt;
驅動程式的種類有[[匯流排驅動程式]]（bus driver）、[[功能驅動程式]]（function driver）、[[篩選驅動程式]]（filter driver）三種：&lt;br /&gt;
*匯流排驅動程式（bus drivers）&lt;br /&gt;
**虛擬匯流排驅動程式（Virtual bus drivers）：呼叫IoInvalidateDeviceRelations通知PnP Manager。&lt;br /&gt;
*功能驅動程式（function drivers）&lt;br /&gt;
**微埠型驅動程式（[[miniport driver]]s）：屬於USB, Audio, SCSI以及network的轉換器（adapters）。&lt;br /&gt;
**虛擬裝置驅動程式（Virtual device drivers）&lt;br /&gt;
**類型驅動程式（Class drivers）&lt;br /&gt;
*篩選性驅動程式（filter drivers）&lt;br /&gt;
**上層篩選性驅動程式（upper-filter drivers）&lt;br /&gt;
**下層篩選性驅動程式（lower-filter drivers）&lt;br /&gt;
&lt;br /&gt;
== 程式進入點 ==&lt;br /&gt;
如同許多語言從main函式開始，WDM驅動程式的載入（Loading）乃至於動作，以及其卸載（Unload）行為，都有其步驟與規則。WDM驅動程式可以動態式的載入與卸載，當偵測到裝置（Device）插入的時候，依據「PnP Manager」會自動地載入相對應的裝置驅動程式，然後成為「Driver Object」，並呼叫DriverEntry函式。所有的WDM驅動程式，都必須擁有這個DriverEntry常式（routine），而且「此一名稱不可改變」的，所有的驅動程式也是從這裡開始執行的，I/O Manager首先呼叫驱动程式的&amp;lt;code&amp;gt;DriverEntry()&amp;lt;/code&amp;gt;。DriverEntry在DDK Compiler編譯出來的輸出符號表是“&amp;lt;code&amp;gt;DriverEntry@8&amp;lt;/code&amp;gt;”，原因是微軟的C編譯器把stdcall函示（例如VcDCall）的名稱加上“記號”，加上一個＠符號，在附上參數的總位元組個數，8指此function的所有參數所佔的byte數。&amp;lt;!--@8的來源是因為寫DLL的程式時，必須要進行函式匯出（export function），除了可以用函式名稱（function name）來匯出（export）外，另一種方式是用序號（by Ordinal），而8正是ENTRY_SUFFIX的值（參考makefile.def與i386mk.inc）。--&amp;gt;&lt;br /&gt;
&lt;br /&gt;
DriverEntry函式有兩個參數，其中第一个参数&amp;lt;code&amp;gt;PDRIVER_OBJECT DriverObject&amp;lt;/code&amp;gt;是指向该驅動程式对应的物件指標；&amp;lt;code&amp;gt;PUNICODE_STRING RegistryPath&amp;lt;/code&amp;gt;，驅動程式的服务主要鍵碼，這個參數的使用時機並不多。以下是一個簡單而標準的DriverEntry基本實作：&lt;br /&gt;
&amp;lt;syntaxhighlight lang=c&amp;gt;&lt;br /&gt;
 NTSTATUS DriverEntry(PDRIVER_OBJECT DriverObject, PUNICODE_STRING pRegistryString)&lt;br /&gt;
 {&lt;br /&gt;
   //PDEVICE_OBJECT DriverObject;&lt;br /&gt;
   UNICODE_STRING deviceName;&lt;br /&gt;
   RtlInitUnicodeString( &amp;amp;deviceName, DEVICE_NAME );&lt;br /&gt;
       &lt;br /&gt;
   status = IoCreateDevice( DriverObject, 0, &amp;amp;deviceName, &lt;br /&gt;
      FILE_DEVICE_UNKNOWN, FILE_DEVICE_SECURE_OPEN, true, &amp;amp;pDeviceObj );&lt;br /&gt;
 &lt;br /&gt;
   UNICODE_STRING linkName;&lt;br /&gt;
   RtlInitUnicodeString( &amp;amp;linkName, LINK_NAME );&lt;br /&gt;
   status = IoCreateSymbolicLink( &amp;amp;linkName, &amp;amp;deviceName );&lt;br /&gt;
 &lt;br /&gt;
   DriverObject-&amp;gt;DriverUnload = DriverUnload;&lt;br /&gt;
   DriverObject-&amp;gt;MajorFunction[IRP_MJ_CREATE] =&lt;br /&gt;
   DriverObject-&amp;gt;MajorFunction[IRP_MJ_CLOSE] =&lt;br /&gt;
   DriverObject-&amp;gt;MajorFunction[IRP_MJ_DEVICE_CONTROL] = xxDriverDispatch;&lt;br /&gt;
   DriverObject-&amp;gt;DriverUnload = xxUnload;&lt;br /&gt;
 &lt;br /&gt;
   return STATUS_SUCCESS;&lt;br /&gt;
 }&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== IRQL ==&lt;br /&gt;
DriverEntry運作在IRQL = PASSIVE_LEVEL等級，所以可以使用分頁內存。WDM有數個經常實作的PASSIVE_LEVEL等級如下：&lt;br /&gt;
&lt;br /&gt;
*DriverEntry&lt;br /&gt;
*Dispatch Function：DispatchXxx&lt;br /&gt;
*Unload：UnloadXxx&lt;br /&gt;
*AddDevice: XxxAddDevice&lt;br /&gt;
*Reinitialize: XxxReinitialize&lt;br /&gt;
&lt;br /&gt;
另外還有幾個DISPATCH_LEVEL等級的函式如下：&lt;br /&gt;
*StartIo&lt;br /&gt;
*AdapterControl &lt;br /&gt;
*ControllerControl&lt;br /&gt;
*IoTimer&lt;br /&gt;
*Dpc（延遲程序呼叫，Deferred Procedure Call）&lt;br /&gt;
&lt;br /&gt;
== 派送行程 ==&lt;br /&gt;
當&amp;#039;&amp;#039;DriverEntry&amp;#039;&amp;#039;函式完成物件的初始化與系統註冊之後，接下來的重點便會落在Dispatch Function身上。每當I/O Manager得到一個請求時（例如按鍵，移動滑鼠），它使用請求的函數代碼（IoControlCode）呼叫驅動程序中幾個Dispatch行程。&lt;br /&gt;
&amp;lt;syntaxhighlight lang=c&amp;gt;&lt;br /&gt;
 NTSTATUS xxDispatch (IN PDEVICE_OBJECT DeviceObject,IN PIRP pIrp)&lt;br /&gt;
 { &lt;br /&gt;
    NTSTATUS ntStatus = STATUS_SUCCESS;&lt;br /&gt;
    ULONG IoControlCodes = 0;             &lt;br /&gt;
    PIO_STACK_LOCATION IrpStack=NULL;   &lt;br /&gt;
 &lt;br /&gt;
    pIrp-&amp;gt;IoStatus.Status = STATUS_SUCCESS;&lt;br /&gt;
    pIrp-&amp;gt;IoStatus.Information = 0;&lt;br /&gt;
 &lt;br /&gt;
    IrpStack = IoGetCurrentIrpStackLocation(pIrp);    &lt;br /&gt;
 &lt;br /&gt;
    switch (IrpStack-&amp;gt;MajorFunction)&lt;br /&gt;
    { &lt;br /&gt;
        case IRP_MJ_CREATE:&lt;br /&gt;
            break;&lt;br /&gt;
        case IRP_MJ_CLOSE:&lt;br /&gt;
            break;&lt;br /&gt;
        case IRP_MJ_DEVICE_CONTROL:&lt;br /&gt;
            IoControlCodes=IrpStack-&amp;gt;Parameters.DeviceIoControl.IoControlCode;&lt;br /&gt;
            switch (IoControlCodes)&lt;br /&gt;
            { &lt;br /&gt;
                case IOCTL_1:&lt;br /&gt;
                    break;&lt;br /&gt;
                case IOCTL_2:&lt;br /&gt;
                    break;&lt;br /&gt;
                default:&lt;br /&gt;
                    pIrp-&amp;gt;IoStatus.Status = STATUS_INVALID_PARAMETER;&lt;br /&gt;
                    break;&lt;br /&gt;
            }&lt;br /&gt;
            break;&lt;br /&gt;
        default:&lt;br /&gt;
            break;&lt;br /&gt;
    }&lt;br /&gt;
    ntStatus=pIrp-&amp;gt;IoStatus.Status;&lt;br /&gt;
 &lt;br /&gt;
    IoCompleteRequest(pIrp,IO_NO_INCREMENT);&lt;br /&gt;
 &lt;br /&gt;
    return ntStatus;&lt;br /&gt;
 }&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== 卸載 ==&lt;br /&gt;
Unload負責在驅動程式被停止前做一些必要的處理動作，如释放资源，记录最後状态等。&lt;br /&gt;
&amp;lt;syntaxhighlight lang=c&amp;gt;&lt;br /&gt;
 VOID DriverUnLoad (IN PDRIVER_OBJECT DriverObject)&lt;br /&gt;
 { &lt;br /&gt;
   if (DeviceObject) {&lt;br /&gt;
   IoUnregisterFileSystem(DeviceObject);&lt;br /&gt;
   IoDeleteDevice(DeviceObject);&lt;br /&gt;
   //DeviceObject = 0;&lt;br /&gt;
 }&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
&lt;br /&gt;
== 編譯 ==&lt;br /&gt;
驅動程式的编译需要使用DDK（&amp;#039;&amp;#039;Device Driver Kit&amp;#039;&amp;#039;）中的build指令，它是一道命令行程序，一般會在後面加上參數：&amp;#039;&amp;#039;&amp;#039;-ceZ&amp;#039;&amp;#039;&amp;#039;。例如：&lt;br /&gt;
&amp;lt;syntaxhighlight lang=dos&amp;gt;&lt;br /&gt;
 C:\driver sample&amp;gt;build.exe -ceZ&lt;br /&gt;
&amp;lt;/syntaxhighlight&amp;gt;&lt;br /&gt;
DDK可用於建立用於 Windows 2000、Windows XP、Microsoft Windows Server 2003、Vista的建置環境，但在Windows作業系統並非預設的功能，必須另行安裝。安装完成後你會看到Build Enviroment，&amp;#039;&amp;#039;&amp;#039;free是指release版，check則是debug版&amp;#039;&amp;#039;&amp;#039;。&lt;br /&gt;
* Windows XP checked 64 Bit Build Environment&lt;br /&gt;
* Windows XP checked Build Environment&lt;br /&gt;
* Windows XP free 64 Bit Build Environment&lt;br /&gt;
* Windows XP free Build Environment&lt;br /&gt;
&lt;br /&gt;
build指令一開始呼叫Build.exe編譯連結器，從系統「環境變數」（Environment Variable）Include中得到引用文件的地址，然後呼叫&amp;#039;&amp;#039;&amp;#039;Visual C++&amp;#039;&amp;#039;&amp;#039;的编译链接器Nmake.exe进行实际的编译链接工作。在編譯過程中遇到的错误，遇到的警告，會記錄到buildxxx.log，buildxxx.wrn，buildxxx.err等文件中。&lt;br /&gt;
&lt;br /&gt;
== 安裝 ==&lt;br /&gt;
安裝過程分成兩個步驟：&lt;br /&gt;
* 首先將编译成的.sys文件複製到Windows NT的System32\\Drivers\\目錄下；&lt;br /&gt;
* 接著在Registry的HKEY_LOCAL_MACHINE\\SYSTEM\\CurrentControlSet\\Services\\下建立和.sys文件同名的键，然后在之下建立名为Start、Type、ErrorControl的三種REG_DWORD類型的键值。&lt;br /&gt;
&lt;br /&gt;
== 範例 ==&lt;br /&gt;
Microsoft DDK提供了大量的WDM範例（samples）參考，這些範例隨著DDK的安裝，會進駐我們的系統之中（WINDDK\xx00\src）。一般人不大可能從輪子造起一個新的驅動程式，大部份要靠“既有的範例”來改良一個新的驅動程式。&lt;br /&gt;
*1394&lt;br /&gt;
*Audio&lt;br /&gt;
*AVStream&lt;br /&gt;
*filesys&lt;br /&gt;
*general&lt;br /&gt;
*hid&lt;br /&gt;
*input&lt;br /&gt;
*ir&lt;br /&gt;
*kernel&lt;br /&gt;
&lt;br /&gt;
== 批評 ==&lt;br /&gt;
* WDM學習曲線過長。&lt;br /&gt;
* 電源管理（power management）事件與隨插即用（Plug-and-play）差異太大。導致系統的睡眠（sleep）與清醒（wake up）狀態容易產生問題。&lt;br /&gt;
* I/O cancellation幾乎不可能達成。&lt;br /&gt;
* 每支驅動程式動輒要撰寫數千行的程式碼。&lt;br /&gt;
* 不支援純使用者模式（pure user-mode）驅動程式。&lt;br /&gt;
&lt;br /&gt;
== 相關條目 ==&lt;br /&gt;
* [[Windows Driver Foundation]]&lt;br /&gt;
*[[Windows Display Driver Model]]&lt;br /&gt;
*[[VxD]]&lt;br /&gt;
&lt;br /&gt;
== 外部連結 ==&lt;br /&gt;
* [https://web.archive.org/web/20080206174045/http://www.microsoft.com/whdc/driver/wdf/default.mspx Windows Driver Foundation Homepage]&lt;br /&gt;
* [https://web.archive.org/web/20091021174351/http://www.wd-3.com/archive/FrameworkIntro.htm Introducing Windows Driver Framework]，written by well-known Windows driver developer, Walter Oney.&lt;br /&gt;
*[https://web.archive.org/web/20060422192541/http://www.codeproject.com/system/wdf_kmdf_basic.asp Building and deploying a basic WDF Kernel Mode Driver]，CodeProject&lt;br /&gt;
*[https://web.archive.org/web/20071014004348/http://www.codeproject.com/system/kmdf_osr_usb_fx2.asp Developing a WDF USB Kernel Mode Driver for the OSR USB FX2]，CodeProject&lt;br /&gt;
* [https://web.archive.org/web/20061106062912/http://www.codeproject.com/system/WDM_Driver_development.asp A simple demo for WDM Driver development]&lt;br /&gt;
&lt;br /&gt;
== 參考 ==&lt;br /&gt;
*Walter Oney，《Windows Driver Model》&lt;br /&gt;
&lt;br /&gt;
{{Microsoft APIs}}&lt;br /&gt;
&lt;br /&gt;
[[Category:微軟API]]&lt;br /&gt;
[[Category:驱动程序]]&lt;/div&gt;</summary>
		<author><name>~2025-33547-29</name></author>
	</entry>
</feed>