天天看點

USB開發—自上而下(四)

聊完了CreateFile的調用過程,我們再來看一看三個非常重要的API函數DeviceIoControl、ReadFile、WriteFile:

BOOL WINAPI DeviceIoControl(
_In_ HANDLE hDevice,
_In_ DWORD dwIoControlCode,
_In_opt_ LPVOID lpInBuffer,
_In_ DWORD nInBufferSize,
_Out_opt_ LPVOID lpOutBuffer,
_In_ DWORD nOutBufferSize,
_Out_opt_ LPDWORD lpBytesReturned,
_Inout_opt_ LPOVERLAPPED lpOverlapped);
           

hDevice—通過CreateFile打開的裝置句柄

dwIoControlCode—應用程式調用驅動程式的控制指令

lpInBuffer—應用程式傳遞到驅動程式資料的緩沖區位址

nInBufferSize—緩沖區長度

nOutBuffer—驅動程式傳回資料到應用程式的緩沖區位址

nOutBufferSize—緩沖區長度

lpBytesReturned—驅動程式實際傳回的資料長度

lpOverlapped—重疊結構,異步調用函數時使用

USB開發—自上而下(四)

DeviceIoControl的調用過程比較簡單,API通過系統調用進入核心,核心中兩次調用ObReferenceObjectByHandle,一次為了擷取句柄對應的裝置對象(實際上是檔案對象),另一次是為了擷取Event句柄對應的事件對象,該對象用于處理使用者模式下的同步問題;順着裝置對象的堆疊往上爬,獲得了頂層裝置對象,之後就準備了一個IRP,通過IoCallDriver調用了驅動程式中的OnMajorDeviceIoControl函數,這些函數前一章已經分析過,了解起來應該不成問題。

BOOL WriteFile(
 HANDLE hFile,
 LPCVOID lpBuffer, 
 DWORD nNumberOfBytesToWrite,
 LPDWORD lpNumberOfBytesWritten,
 LPOVERLAPPED lpOverlapped
);
           

hFile—通過CreateFile打開的裝置句柄

lpBuffer—應用程式傳遞到驅動程式資料的緩沖區位址

nNumberOfBytesToWrite—緩沖區長度

lpNumberOfBytesWriten—實際寫操作的長度

lpOverlapped—重疊結構,異步調用函數時使用

USB開發—自上而下(四)
BOOL ReadFile(
    HANDLE hFile,
    LPVOID lpBuffer,
    DWORD nNumberOfBytesToRead,
    LPDWORD lpNumberOfBytesRead,
    LPOVERLAPPED lpOverlapped
    );
           

hFile—通過CreateFile打開的裝置句柄

lpBuffer—驅動程式傳回資料到應用程式的緩沖區位址

nNumberOfBytesToRead—緩沖區長度

lpNumberOfBytesRead—驅動程式實際傳回的資料長度

lpOverlapped—重疊結構,異步調用函數時使用

USB開發—自上而下(四)

從上面的函數調用圖可以看出:

1, WriteFile、ReadFile、DeviceIoControl三個函數異曲同工,走的路線很相近

2, 在windows核心層,WriteFile生成一個MajorFunction為IRP_MJ_WRITE的IRP

        ReadFile生成一個MajorFunction為IRP_MJ_READ的IRP

        DeviceIoControl生成一個MajorFunction為IRP_MJ_DEVICE_CONTROL的IRP

3, 在windows核心層,WriteFile函數生成的IO_STACK_LOCATION消息參數聯合體需要轉換成Write結構體

       ReadFile函數生成的IO_STACK_LOCATION消息參數聯合體需要轉換成Read結構體

       DeviceIoControl函數生成的IO_STACK_LOCATION消息參數聯合體需要轉換成DeviceIoControl結構體

4, 隻要驅動支援,WriteFile,ReadFile完全可以由DeviceIoControl替代

參考資料: 

1, <<Windows核心情景分析>>

繼續閱讀