WdfUsbTargetPipeReadSynchronously 関数 (wdfusb.h)

[KMDF と UMDF に適用]

WdfUsbTargetPipeReadSynchronously メソッドは、読み取り要求をビルドし、指定された USB 入力パイプに同期的に送信します。

構文

NTSTATUS WdfUsbTargetPipeReadSynchronously(
  [in]            WDFUSBPIPE                Pipe,
  [in, optional]  WDFREQUEST                Request,
  [in, optional]  PWDF_REQUEST_SEND_OPTIONS RequestOptions,
  [in, optional]  PWDF_MEMORY_DESCRIPTOR    MemoryDescriptor,
  [out, optional] PULONG                    BytesRead
);

パラメーター

[in] Pipe

WdfUsbInterfaceGetConfiguredPipe を呼び出して取得されたフレームワーク パイプ オブジェクトへのハンドル。

[in, optional] Request

フレームワーク要求オブジェクトへのハンドル。 このパラメーターは省略可能であり、 NULL にすることができます。 詳細については、「解説」を参照してください。

[in, optional] RequestOptions

要求のオプションを指定する呼び出し元によって割り当てられた WDF_REQUEST_SEND_OPTIONS 構造体へのポインター。 このポインターは省略可能であり、 NULL にすることができます。 詳細については、「解説」を参照してください。

[in, optional] MemoryDescriptor

デバイスからデータを受信するバッファーを記述する呼び出し元によって割り当てられた WDF_MEMORY_DESCRIPTOR 構造体へのポインター。 ドライバーが WdfUsbTargetPipeSetNoMaximumPacketSizeCheck を呼び出していない限り、バッファー サイズはパイプの最大パケット サイズの倍数である必要があります。 このバッファーの詳細については、次の「備考」セクションを参照してください。

[out, optional] BytesRead

操作が成功した場合に読み取られたバイト数を受け取る場所へのポインター。 このパラメーターは省略可能であり、 NULL にすることができます。

戻り値

操作が成功した場合、WdfUsbTargetPipeReadSynchronously は I/O ターゲットの完了状態値を返します。 それ以外の場合、このメソッドは次のいずれかの値を返すことができます。

リターン コード 説明
STATUS_INFO_LENGTH_MISMATCH
RequestOptions によって指されたWDF_REQUEST_SEND_OPTIONS構造体のサイズが正しくありません。
STATUS_INVALID_PARAMETER
無効なパラメーターが検出されました。
STATUS_INSUFFICIENT_RESOURCES
メモリが不足していました。
STATUS_INVALID_DEVICE_REQUEST
呼び出し元の IRQL がPASSIVE_LEVELされていない、無効なメモリ記述子が指定された、パイプの型が無効、転送方向が無効、または指定した I/O 要求が既に I/O ターゲットにキューに登録されている。
STATUS_INVALID_BUFFER_SIZE
バッファー サイズは、パイプの最大パケット サイズの倍数ではありません。
STATUS_IO_TIMEOUT
ドライバーはタイムアウト値を指定し、割り当てられた時間内に要求が完了しませんでした。
STATUS_REQUEST_NOT_ACCEPTED
要求パラメーターが表す I/O 要求パケット (IRP) は、ドライバーが 要求 を転送できるようにするため の十 分なIO_STACK_LOCATION構造を提供しません。
 

このメソッドは、他の NTSTATUS 値を返す場合もあります。

ドライバーが無効なオブジェクト ハンドルを提供すると、バグ チェックが発生します。

注釈

読み取り要求を同期的に送信するには、 WdfUsbTargetPipeReadSynchronously メソッドを使用します。 読み取り要求を非同期に送信するには、 WdfUsbTargetPipeFormatRequestForRead を使用し、その後に WdfRequestSend を使用します。

Pipe パラメーターが指定する パイプ は入力パイプである必要があり、パイプの 種類WdfUsbPipeTypeBulk または WdfUsbPipeTypeInterrupt である必要があります。

WdfUsbTargetPipeReadSynchronously メソッドは、要求が完了するまで、RequestOptions パラメーターが指すWDF_REQUEST_SEND_OPTIONS構造体にタイムアウト値を指定しない限り、またはエラーが検出されない限り、戻りません。

ドライバーが I/O キューで受信した I/O 要求を転送することも、新しい要求を作成して送信することもできます。 どちらの場合も、フレームワークには要求オブジェクトとバッファー領域が必要です。

ドライバーが I/O キューで受信した I/O 要求を転送するには:

  1. Request パラメーターに対して、受信した 要求 のハンドルを指定します。
  2. WdfUsbTargetPipeReadSynchronously メソッドの MemoryDescriptor パラメーターには、受信した要求の出力バッファーを使用します。

    ドライバーは WdfRequestRetrieveOutputMemory を呼び出して、要求の出力バッファーを表すフレームワーク メモリ オブジェクトへのハンドルを取得し、そのハンドルを MemoryDescriptor が指すWDF_MEMORY_DESCRIPTOR構造体に配置する必要があります。

I/O 要求の転送の詳細については、「I /O 要求の転送」を参照してください。

ドライバーは、多くの場合、受信した I/O 要求を、I/O ターゲットに送信する小さな要求に分割するため、ドライバーが新しい要求を作成する可能性があります。

新しい I/O 要求を作成するには:

  1. WdfUsbTargetPipeReadSynchronously メソッドの Request パラメーターに NULL 要求ハンドルを指定するか、新しい要求オブジェクトを作成してそのハンドルを指定します。
    • NULL 要求ハンドルを指定すると、フレームワークは内部要求オブジェクトを使用します。 この手法は簡単に使用できますが、ドライバーは要求をキャンセルできません。
    • WdfRequestCreate を呼び出して 1 つ以上の要求オブジェクトを作成する場合は、WdfRequestReuse を呼び出すことで、これらの要求オブジェクトを再利用できます。 この手法を使用すると、ドライバーの EvtDriverDeviceAdd コールバック関数を使用して、デバイスの要求オブジェクトを事前に割り当てできます。 さらに、別のドライバー スレッドは WdfRequestCancelSentRequest を呼び出して、必要に応じて要求を取り消すことができます。

    ドライバーは、NULL 以外の RequestOptions パラメーターを指定できます。これは、ドライバーが NULL 以外の要求パラメーターまたは NULL要求パラメーターを提供するかどうかです。 たとえば、 RequestOptions パラメーターを使用してタイムアウト値を指定できます。

  2. WdfUsbTargetPipeReadSynchronously メソッドの MemoryDescriptor パラメーターのバッファー領域を指定します。

    ドライバーでは、ローカルに割り当てられたバッファーとして、WDFMEMORY ハンドルとして、または MDL として、このバッファー領域を指定できます。 最も便利な方法を使用できます。

    必要に応じて、フレームワークはバッファー記述を、データ バッファーにアクセスするための I/O ターゲットの メソッドに適した記述に変換します

    次の手法を使用できます。

    • ローカル バッファーを指定する

      WdfUsbTargetPipeReadSynchronously は I/O 要求を同期的に処理するため、次のコード例に示すように、ドライバーは呼び出し元ルーチンに対してローカルな要求バッファーを作成できます。

      WDF_MEMORY_DESCRIPTOR  memoryDescriptor;
      MY_BUFFER_TYPE  myBuffer;
      WDF_MEMORY_DESCRIPTOR_INIT_BUFFER(&memoryDescriptor,
                                        (PVOID) &myBuffer,
                                        sizeof(myBuffer));
      
    • WDFMEMORY ハンドルを指定する

      次のコード例に示すように、 WdfMemoryCreate または WdfMemoryCreatePreallocated を呼び出して、フレームワークマネージド メモリへのハンドルを取得します。

      WDF_MEMORY_DESCRIPTOR  memoryDescriptor;
      WDFMEMORY  memoryHandle = NULL;
      status = WdfMemoryCreate(NULL,
                               NonPagedPool,
                               POOL_TAG,
                               MY_BUFFER_SIZE,
                               &memoryHandle,
                               NULL);
      WDF_MEMORY_DESCRIPTOR_INIT_HANDLE(&memoryDescriptor,
                                        memoryHandle,
                                        NULL);
      

      または、ドライバーは WdfRequestRetrieveOutputMemory を呼び出して、受信した I/O 要求の出力バッファーを表すフレームワーク メモリ オブジェクトへのハンドルを取得できます (ドライバーがそのバッファーの内容を I/O ターゲットに渡す場合)。 WdfUsbTargetPipeReadSynchronously が I/O ターゲットに送信する新しい要求が削除、再利用、または再フォーマットされるまで、ドライバーは受信した I/O 要求を完了してはなりません。 (WdfUsbTargetPipeReadSynchronously は、メモリ オブジェクトの参照カウントをインクリメントします。要求オブジェクトを削除、再利用、または再フォーマットすると、メモリ オブジェクトの参照カウントがデクリメントされます)。

    • MDL を指定する

      ドライバーは、 WdfRequestRetrieveOutputWdmMdl を呼び出すことによって、受信した I/O 要求に関連付けられている MDL を取得できます。

フレームワークは、内部 URB に USBD_SHORT_TRANSFER_OK フラグを設定します。 このフラグを設定すると、データ転送の最後のパケットが最大パケット サイズより小さくなります。

ドライバーは、パイプの連続リーダーを構成している場合、WdfUsbTargetPipeReadSynchronously を呼び出すことはできません。

I/O 要求の完了後に状態情報を取得する方法については、「 完了情報の取得」を参照してください。

WdfUsbTargetPipeReadSynchronously メソッドと USB I/O ターゲットの詳細については、「USB I/O ターゲット」を参照してください。

次のコード例では、フレームワーク メモリ オブジェクトを作成し、 WDF_MEMORY_DESCRIPTOR 構造体を初期化し、その構造体を WdfUsbTargetPipeReadSynchronously に渡します。 この例では、要求オブジェクト ハンドルに NULL を 指定するため、フレームワークは I/O ターゲットの新しい要求オブジェクトを作成します。

WDFMEMORY  wdfMemory;
WDF_MEMORY_DESCRIPTOR  readBufDesc;
ULONG  BytesRead;

status = WdfMemoryCreate(
                         WDF_NO_OBJECT_ATTRIBUTES,
                         NonPagedPool,
                         0,
                         readSize,
                         &wdfMemory,
                         NULL
                         );
if (!NT_SUCCESS(status)){
    return ;
}

buffer = WdfMemoryGetBuffer(
                            wdfMemory,
                            NULL
                            );

WDF_MEMORY_DESCRIPTOR_INIT_BUFFER(
                                  &readBufDesc,
                                  buffer,
                                  readSize
                                  );

status = WdfUsbTargetPipeReadSynchronously(
                                           Pipe,
                                           NULL,
                                           NULL,
                                           &readBufDesc,
                                           &BytesRead
                                           );

要件

要件
対象プラットフォーム ユニバーサル
最小 KMDF バージョン 1.0
最小 UMDF バージョン 2.0
Header wdfusb.h (Wdfusb.h を含む)
Library Wdf01000.sys (KMDF);WUDFx02000.dll (UMDF)
IRQL PASSIVE_LEVEL
DDI コンプライアンス規則 DriverCreate(kmdf)InternalIoctlReqs(kmdf)IoctlReqs(kmdf)KmdfIrql(kmdf)KmdfIrql2(kmdf)、KmdfIrqlExplicit(kmdf)、 SyncReqSend(kmdf)UsbKmdfIrql(kmdf)UsbKmdfIrql2(kmdf)、UsbKmdfIrqlExplicit( kmdf)、WriteReqs(kmdf)

こちらもご覧ください

WDF_MEMORY_DESCRIPTOR_INIT_BUFFER

WdfMemoryCreate

WdfUsbTargetPipeGetInformation