windows驅動開發總結

基本概念

這裏說的驅動主要指內核模塊,並不一定指設備驅動

數據結構

  • 驅動對象。一個驅動對象代表了一個驅動程序或內核模塊。其中的分發函數比較重要
  • 設備對象。設備對象是IRP作用的實體,它們接收和發送IRP。一個設備對象可以代表實際的硬件設備,也可以代表一個抽象的概念。一個設備對象總是屬於某一個驅動對象。
  • IRP請求。一個請求包含要傳輸的所有信息,是一個十分複雜的結構,其中的主功能號是用於區分請求類型。

水平層級:一個驅動對象可以創建多個設備對象,這些設備對象處於同位關係,在層次上是水平的

垂直層級:使用DeviceObject->AttachedDeviced可以找到上層設備。一個設備可以附加到另一個設備上,以此成爲一個設備棧。而每個設備屬於一個驅動,因此驅動也成了一個垂直結構。

設備擴展:設備擴展是一個自定義結構,開發者可以將所需的內核信息定義到其中。在每個設備對象中有一個DeviceExtension字段,該字段指向一塊未初始化的內存塊,我們創建的設備擴展就可以放到這裏。

過濾:wdm模型驅動至少由兩層設備來完成工作,最底層的是物理設備(PDO),上層的是功能設備(FDO)。因此,我們要對向設備發送或接收的數據進行攔截和過濾,可以在這兩層之間插入一層來達到目的。

NT驅動與WDM驅動的區別:說白了就是wdm是pnp管理器管理的,通過.inf加載的即插即用驅動;而nt是IO管理器管理的,需要通過服務來加載。

程序流程

  • 入口函數:每個驅動程序都有一個入口點DriverEntry,它完成一些初始化的工作,如指定分發函數,創建設備,附加設備,創建鏈接等,它傳入兩個參數,參數一是驅動對象自身,參數二是驅動在註冊表中的路徑。
  • 分發函數:一旦一個設備接收到了IRP請求後,系統就會去調用驅動的Dispatch函數,該函數對相應的IRP請求進行處理,其中如何進行處理是根據IRP的主功能號來決定的,它代表請求的類型。
  • 卸載函數:當驅動要被卸載時,需要完成一些收尾的工作,比如脫離附加設備,刪除鏈接,刪除設備等。

常用API

附加設備。該函數附加到一個設備所屬的設備棧的頂層,並返回低一級的設備指針

PDEVICE_OBJECT IoAttachDeviceToDeviceStack(PDEVICE_OBJECT*, PEDIVCE_OBJECT*)

根據名字獲取一個對象指針(內核函數,未文檔化,可以聲明後直接使用)

ObReferenceObjectByName

跳過本層對IRP請求,直接分發到下一層

IoSkipCurrentIrpStackLocation
IoCallDriver

對下層驅動處理完成後返回的IRP進行處理

IoCopyCurrentIrpStackLocationToNext
IoSetCompletionRoutine //設置處理完成後的回調函數
IoCallDriver

WDF(Windows Driver Framework)

WDF是用於開發驅動的一個框架,它對一些驅動的流程進行了封裝。在入口點函數中,通常會調用WDF_DRIVER_CONFIG_INIT函數來設置DeviceAdd函數,該函數是一個回調函數,一旦發現有設備出現,系統就會調用該函數來創建設備對象。

通常來說,在DeviceAdd函數中會創建設備對象和IRP隊列,對IRP隊列的分發函數進行設置,以及創建設備鏈接。

感覺沒啥好說的…看文檔就行

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章