バッファー付き I/O を使用した DispatchReadWrite

バッファー I/O のデバイス オブジェクトを設定する最下位レベルのデバイス ドライバーは、Irp->AssociatedIrp.SystemBuffer でロックダウンされたシステム領域バッファーにデバイスから転送されたデータを返すことによって、読み取り要求を満たします。 また同じバッファーからデバイスにデータを転送することで、書き込み要求を満たします。

したがって、このようなデバイス ドライバーの DispatchReadWrite ルーチンは、通常、転送要求の受信時に次の処理を行います。

  1. IoGetCurrentIrpStackLocation を呼び出して、転送要求の方向を決定します。

  2. 要求のパラメーターの有効性を確認します。

    • 読み取り要求の場合、通常、ルーチンはドライバーの IoStackLocation->Parameters.Read.Length 値をチェックして、バッファーがデバイスから転送されたデータを受信するのに十分な大きさであるかどうかを判断します。

      たとえば、システム キーボード クラス ドライバーは、Win32 ユーザー入力スレッドから受信する読み取り要求のみを処理します。 このドライバーは、デバイスからのキー入力を格納する構造体 KEYBOARD_INPUT_DATA を定義し、読み出し要求が来たときにそれを満たすために、任意の時点で、これらの構造体のいくつかを内部リングバッファに保持します。

    • 書き込み要求に対して、このルーチンは通常、Parameters.Write.Length の値をチェックし、必要に応じて Irp->AssociatedIrp.SystemBuffer のデータが有効かどうか、つまり、そのデバイスが値範囲が定義されたメンバーを含む構造化データ パケットのみを受け入れるかどうかを確認します。

  3. いずれかのパラメーターが無効な場合、DispatchReadWrite ルーチンは即座に IRP を完了します (前述の「ドライバー スタックへの IRP の受け渡し」の説明を参照)。 そうでない場合、ルーチンは他のドライバー ルーチンに IRP を渡してさらに処理します (「ドライバー スタックへの IRP の受け渡し」を参照)。

バッファー I/O を使用する最下位デバイス ドライバーは、通常、要求の発信元が指定したサイズのデータの読み取りまたは書き込みによって転送要求を満たす必要があります。 このようなドライバーは、多くの場合、デバイスから受信またはデバイスに送信されるデータの構造を定義し、システム キーボード クラス ドライバーと同様に、構造化データを内部的にバッファー処理します。

データを内部的にバッファーするドライバーは、IRP_MJ_FLUSH_BUFFERS 要求をサポートする必要があります。また、IRP_MJ_SHUTDOWN 要求をサポートすることもできます。

通常、チェーンの最上位ドライバーは、下位ドライバーに読み取り/書き込み要求を渡す前に、入力 IRP のパラメーターをチェックすることが求められます。 そのため、多くの下位レベルのドライバーは、読み取り/書き込み IRP 内の I/O スタック位置にあるパラメーターが有効であると想定できます。 チェーン内の最下位レベルのドライバーが、データ転送に関するデバイス固有の制約を認識している場合、そのドライバーは、その I/O スタックの場所でパラメーターの有効性をチェックする必要があります。