IRP_MN_QUERY_ALL_DATA
WMI をサポートするすべてのドライバーは、この IRP を処理する必要があります。 ドライバーは、「WMI 要求の処理」で説明されているように、WmiSystemControl を呼び出すか、ドライバー自身で IRP を処理することによって、WMI IRP を処理できます。
ドライバーが WmiSystemControl を呼び出して IRP_MN_QUERY_ALL_DATA 要求を処理すると、WMI はそのドライバーの DpWmiQueryDataBlock ルーチンを呼び出します。
主要なコード
送信時
WMI は、特定のデータ ブロックのすべてのインスタンスに対してクエリを実行するために、この IRP を送信します。
WMI は任意のスレッド コンテキストで、IRQL = PASSIVE_LEVEL でこの IRP を送信します。
入力パラメーター
IRP のドライバーの I/O スタック位置の Parameters.WMI.ProviderId は、要求に応答する必要があるドライバーのデバイス オブジェクトを指します。
Parameters.WMI.DataPath は、データ ブロックを識別する GUID を指します。
Parameters.WMI.BufferSize は、要求から出力データを受信する Parameters.WMI.Buffer の、ページングされていないバッファーの最大サイズを示します。 バッファー サイズは、返されるすべてのインスタンスのインスタンス名とデータのサイズに sizeof(WNODE_ALL_DATA) を加えたサイズ以上である必要があります。
出力パラメーター
ドライバーが WmiSystemControl を呼び出して WMI IRP を処理すると、WMI はドライバーによって登録された各ブロックに対し、ドライバーの DpWmiQueryDataBlock ルーチンを 1 回呼び出すことによって、WNODE_ALL_DATA を埋めます。
それ以外の場合は、ドライバーは Parameters.WMI.Buffer の WNODE_ALL_DATA 構造体を次のように入力します。
WnodeHeader.BufferSize を返される WNODE_ALL_DATA 全体のバイト数に設定し、WnodeHeader.Timestamp を KeQuerySystemTime によって返される値に設定して、WnodeHeader.Flags を返されるデータに応じて設定します。
InstanceCount に、返されるインスタンスの数を設定します。
ブロックで動的インスタンス名が使用されている場合は、OffsetInstanceNameOffsets を、WNODE_ALL_DATA の先頭から ULONG オフセットの配列が開始する位置までのオフセット (バイト単位) に設定します。 この配列内の各要素は、各動的インスタンス名が格納されている WNODE_ALL_DATA からのオフセットです。 各動的インスタンス名は、カウントされた Unicode 文字列として格納されます。カウントは USHORT の後に Unicode 文字列が続きます。 カウントには、Unicode 文字列の一部である可能性がある終端の null 文字は含まれません。 Unicode 文字列に終端の null 文字が含まれている場合でも、この null 文字は WNodeHeader.BufferSize で確立されたサイズに収まる必要があります。
すべてのインスタンスが同じサイズの場合:
- WnodeHeader.Flags に WNODE_FLAG_FIXED_INSTANCE_SIZE を設定し、FixedInstanceSize をそのサイズ (バイト単位) に設定します。
- DataBlockOffset から始まるインスタンス データをパディングで書き込み、各インスタンスが 8 バイト境界に揃うようにします。 たとえば、FixedInstanceSize が 6 の場合、ドライバーはインスタンス間に 2 バイトのパディングを追加します。
インスタンスのサイズが異なる場合:
WnodeHeader.Flags でWNODE_FLAG_FIXED_INSTANCE_SIZEをクリアし OffsetInstanceDataAndLength offsetInstanceDataAndLength offsetInstanceDataAndLength から始まる構造体の 配列を書き込みます。 各 OFFSETINSTANCEDATAANDLENGTH 構造体は、WNODE_ALL_DATA 構造体の先頭から各インスタンスのデータの先頭までのオフセット (バイト単位) とデータの長さを指定します。 DataBlockOffset は使用されません。
OffsetInstanceDataAndLength 配列の最後の要素の後にインスタンス データを書き込み、各インスタンスが 8 バイトの境界に整列するようにパディングを行います。
Parameters.WMI.Buffer のバッファーが小さすぎてすべてのデータを受け取れない場合、ドライバーは Parameters.WMI.Buffer の WNODE_TOO_SMALL 構造体に必要なサイズを入力します。 バッファーが sizeof(WNODE_TOO_SMALL) より小さい場合、ドライバーは IRP に失敗し、STATUS_BUFFER_TOO_SMALL を返します。
I/O 状態ブロック
ドライバーが WmiSystemControl を呼び出して IRP を処理する場合、WMI は I/O 状態ブロックで Irp->IoStatus.Status と Irp->IoStatus.Information を設定します。
それ以外の場合、ドライバーは Irp->IoStatus.Status を STATUS_SUCCESS または次のような適切なエラー状態に設定します。
STATUS_BUFFER_TOO_SMALL
STATUS_WMI_GUID_NOT_FOUND
成功した場合、ドライバーは Irp->IoStatus.Information を Parameters.WMI.Buffer でバッファーに書き込まれたバイト数に設定します。
操作
ドライバーは、「WMI 要求の処理」で説明されているように、WmiSystemControl を呼び出すか、ドライバー自身で IRP を処理することによって、WMI IRP を処理できます。
ドライバーが WmiSystemControl を呼び出して WMI IRP を処理すると、そのルーチンはドライバーの DpWmiQueryDataBlock ルーチンを呼び出します。
ドライバーが IRP_MN_QUERY_ALL_DATA 要求を処理する場合は、Parameters.WMI.ProviderId が、ドライバーが IoWMIRegistrationControl に渡したのと同じデバイス オブジェクトを指している場合にのみ、ドライバーはこの処理を行う必要があります。 それ以外の場合、ドライバーは、次の下位ドライバーに要求を転送する必要があります。
要求を処理する前に、ドライバーは、Parameters.WMI.DataPath がドライバーがサポートしている GUID を指しているかどうかを判断する必要があります。 指してない場合は、ドライバーは IRP に失敗し、STATUS_WMI_GUID_NOT_FOUND を返す必要があります。
ドライバーがデータ ブロックをサポートしている場合は、次の操作を行う必要があります。
ドライバーから返されるすべてのデータを受け取るのに十分な大きさのバッファーが、Parameters.WMI.BufferSize で指定されていることを確認します。
Parameters.WMI.Buffer の WNODE_ALL_DATA 構造体に、そのデータ ブロックのすべてのインスタンスのデータを入力します。
要件
ヘッダー |
Wdm.h (Wdm.h、Ntddk.h、Ntifs.h を含む) |