對 Windows驅動開發技術詳解 第九章的(IRP的同步)自我理解

對 Windows驅動開發技術詳解 第九章的(IRP的同步)自我理解

BY:ALALMN—飛龍   QQ:316118740     BLOG:http://hi.baidu.com/alalmn
同步異步處理(這個也都是很好理解的) 在R0和R3下都給了例子
///////////////////////////////////////////////////////////////////////////////
同步操作設備
用戶函數 打開設備
HANDLE CreateFile(
  LPCTSTR lpFileName, //指向文件名的指針
  DWORD dwDesiredAccess, //訪問模式(寫/讀)
  DWORD dwShareMode, //共享模式
  LPSECURITY_ATTRIBUTES lpSecurityAttributes, //指向安全屬性的指針
  DWORD dwCreationDisposition, //如何創建
  DWORD dwFlagsAndAttributes, //文件屬性
  HANDLE hTemplateFile //用於複製文件句柄
  );

用戶函數 讀取數據
BOOL ReadFile(
  HANDLE hFile, //文件的句柄
  LPVOID lpBuffer, //用於保存讀入數據的一個緩衝區
  DWORD nNumberOfBytesToRead, //要讀入的字符數
  LPDWORD lpNumberOfBytesRead, //指向實際讀取字節數的指針
  LPOVERLAPPED lpOverlapped //如文件打開時指定了FILE_FLAG_OVERLAPPED,那麼必須,用這個參數引用一個特殊的結構。該結構定義了一次異步讀取操作。否則,應將這個參數設爲NULL
  );

///////////////////////////////////////////////////////////////////////////////
異步操作設備
  typedef struct _OVERLAPPED{
  DWORD Internal;//操作系統保留,指出一個和系統相關的狀態
  DWORD InternalHigh;//指出發送或接收的數據長度
  DWORD Offset;//文件傳送的開始位置
  DWORD OffsetHigh;//文件傳送的字節偏移量的高位字
  HANDLE hEvent;//指定一個I/O操作完成後觸發的事件
  }OVERLAPPED;
在使用OVERLAPPED結構前,先要對其內部清零,並且爲其創建事件。

ReadFile和WriteFile即可以支持同步讀寫操作,又可以支持異步讀寫操作。
ReadFileEx和WriteFileEx函數是專門用於異步讀寫操作的,不能進行同步讀寫。
BOOL ReadFileEx(
HANDLE hFile,                  //設備句柄
LPVOID lpBuffer,               //讀取緩衝區
DWORD nNumberOfBytesToRead,    //讀取的字節數
LPOVERLAPPED lpOverlapped,     //offset指針
LPOVERLAPPED_COMPLETION_ROUTINE lpCompletionRoutine //完成函數
);

錯誤報告
FileIOCompletionRoutine( 
DWORD dwErrorCode;//0:表示操作完成;ERROR_HANDLE_EOF:表示已經到了文件尾端 
DWORD dwNumberOfBytesTransferred;//真正被傳輸的數據字節數 
LPOVERLAPPED lpOverlapped;//由開啓overlapped I/O 操作的函數提供 
);

///////////////////////////////////////////////////////////////////////////////
取消IRP
PDRIVER_CANCEL 
IoSetCancelRoutine(
    IN PIRP Irp,                      //這個參數是需要取消的IRP
    IN PDRIVER_CANCEL CancelRoutine   //這個是取消函數的函數指針。一旦IRP請求被取消的時候,操作系統會調用這個取消函數。
    );

///////////////////////////////////////////////////////////////////////////////
StartiO例程
系統提供了一個IRP隊列來實現串行,這個隊列用KDEVICE_QUEUE數據結構表示。
typedef struct _KDEVICE_QUEUE {
CSHORT Type;
CSHORT Size;
LIST_ENTRY devicelisthead;
KSPIN_LOCK Lock;
BOOLEAN Busy;
} KDEVICE_QUEUE, *PKDEVICE_QUEUE, *RESTRICTED_POINTER PRKDEVICE_QUEUE;

插入隊列的內核函數是KeInsertDeviceQueue
BOOLEAN 
KeInsertDeviceQueue(
    IN PKDEVICE_QUEUE DeviceQueue,            //這個參數是需要被插入的隊列
    IN PKDEVICE_QUEUE_ENTRY DeviceQueueEntry //這個參數是要被插入的元素
    );

刪除隊列元素函數是KeRemoveDeviceQueue
PKDEVICE_QUEUE_ENTRY 
KeRemoveDeviceQueue(
    IN PKDEVICE_QUEUE DeviceQueue   //指定從哪個隊列中取出元素
    );

///////////////////////////////////////////////////////////////////////////////
中斷服務例程(ISR)
ISR函數同步的內核函數KeSynchronizeExecution
BOOLEAN 
KeSynchronizeExecution(
    IN PKINTERRUPT    Interrupt,                     //這個參數是中斷對象指針,ISR和這個對象關聯着。
    IN PKSYNCHRONIZE_ROUTINE SynchronizeRoutine,    //將當前IRQL提升至中斷對象相應的DIRQL,並執行SynchronizeRoutine函數
    IN PVOID SynchronizeContext                     //爲SynchronizeRoutine提供的參數
    );

///////////////////////////////////////////////////////////////////////////////
使用DPC例程,首先要初始化DPC對象,該動作使用內核函數KeInitializeDpc
VOID 
KeInitializeDpc(
    IN PRKDPC Dpc,                          //需要初始化的DPC對象指針
    IN PKDEFERRED_ROUTINE DeferredRoutine, //與DPC關聯的DPC例程
    IN PVOID DeferredContext                //傳入DPC例程的參數
    );

///////////////////////////////////////////////////////////////////////////////

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