Функция WdfUsbTargetDeviceSendControlTransferSynchronously (wdfusb.h)

[Применимо к KMDF и UMDF]

Метод WdfUsbTargetDeviceSendControlTransferSynchronous создает запрос на передачу USB и отправляет его в целевой объект ввода-вывода синхронно.

Синтаксис

NTSTATUS WdfUsbTargetDeviceSendControlTransferSynchronously(
  [in]            WDFUSBDEVICE                  UsbDevice,
  [in, optional]  WDFREQUEST                    Request,
  [in, optional]  PWDF_REQUEST_SEND_OPTIONS     RequestOptions,
  [in]            PWDF_USB_CONTROL_SETUP_PACKET SetupPacket,
  [in, optional]  PWDF_MEMORY_DESCRIPTOR        MemoryDescriptor,
  [out, optional] PULONG                        BytesTransferred
);

Параметры

[in] UsbDevice

Дескриптор объекта USB-устройства, полученный из предыдущего вызова WdfUsbTargetDeviceCreateWithParameters.

[in, optional] Request

Дескриптор объекта запроса платформы. Этот параметр является необязательным и может быть null. Дополнительные сведения см. в следующем разделе "Примечания".

[in, optional] RequestOptions

Указатель на структуру, выделенную вызывающим объектом, WDF_REQUEST_SEND_OPTIONS, которая задает параметры запроса. Этот указатель необязателен и может быть null. Дополнительные сведения см. в следующем разделе "Примечания".

[in] SetupPacket

Указатель на выделенную вызывающим WDF_USB_CONTROL_SETUP_PACKET структуру, описывающую передачу элемента управления.

[in, optional] MemoryDescriptor

Указатель на структуру, выделенную вызывающим объектом, WDF_MEMORY_DESCRIPTOR, которая описывает входные данные или выходной буфер в зависимости от команды для конкретного устройства. Этот указатель необязателен и может быть null. Дополнительные сведения см. в следующем разделе "Примечания".

[out, optional] BytesTransferred

Указатель на расположение, которое получает количество передаваемых байтов. Этот параметр является необязательным и может быть null.

Возвращаемое значение

WdfUsbTargetDeviceSendControlTransferSynchronous возвращает значение состояния завершения целевого объекта ввода-вывода, если операция выполнена успешно. В противном случае этот метод может вернуть одно из следующих значений:

Возвращаемый код Описание
STATUS_INVALID_PARAMETER
Обнаружен недопустимый параметр.
STATUS_INSUFFICIENT_RESOURCES
Недостаточно памяти было доступно.
STATUS_INVALID_DEVICE_REQUEST
Указан недопустимый дескриптор памяти, или указанный запрос ввода-вывода уже помещался в целевой объект ввода-вывода.
STATUS_IO_TIMEOUT
Драйвер предоставил значение времени ожидания и запрос не завершился в течение выделенного времени.
 

Этот метод также может возвращать другие значения NTSTATUS.

Ошибка возникает, если драйвер предоставляет недопустимый дескриптор объекта.

Замечания

Используйте метод WdfUsbTargetDeviceSendControlTransferSynchronous для отправки запроса передачи USB-элемента управления синхронно. Чтобы отправлять такие запросы асинхронно, используйте WdfUsbTargetDeviceFormatRequestForControlTransfer, а затем WdfRequestSend.

Метод WdfUsbTargetDeviceSendControlTransferSynchronous не возвращается до завершения запроса, если драйвер не предоставляет время ожидания в структуре WDF_REQUEST_SEND_OPTIONS, на которую указывает параметр RequestOptions или если ошибка не обнаружена.

Вы можете пересылать запрос ввода-вывода, полученный драйвером в очереди ввода-вывода, или создать и отправить новый запрос. В любом случае для платформы требуется объект запроса и, в зависимости от типа передачи элемента управления, возможно, некоторого буферного пространства.

Чтобы перенаправить запрос ввода-вывода, полученный драйвером в очереди ввода-вывода:

  1. Укажите дескриптор полученного запроса для параметра запроса .
  2. Используйте входной или выходной буфер полученного запроса для параметра MemoryDescriptor.

    Драйвер может вызывать WdfRequestRetrieveInputMemory или WdfRequestRetrieveOutputMemory, чтобы получить дескриптор для объекта памяти платформы, представляющего входной или выходной буфер запроса, а затем поместить этот дескриптор в структуру WDF_MEMORY_DESCRIPTOR, которую драйвер предоставляет для параметра MemoryDescriptor.

Чтобы создать и отправить новый запрос, выполните приведенные ниже действия.
  1. Укажите дескриптор запроса NULL в параметре запроса или создайте новый объект запроса и предоставьте его дескриптор:
    • Если вы предоставляете дескриптор запроса NULL, платформа использует внутренний объект запроса. Этот метод прост в использовании, но драйвер не может отменить запрос.
    • При вызове WdfRequestCreate для создания одного или нескольких объектов запроса можно повторно использовать эти объекты запроса, вызвав WdfRequestReuse. Этот метод позволяет драйвера EvtDriverDeviceAdd функцию обратного вызова для предварительного размещения объектов запросов для устройства. Кроме того, другой поток драйвера может вызывать WdfRequestCancelSentRequest, чтобы отменить запрос при необходимости.

    Драйвер может указать параметр, отличный отNULLRequestOptions, предоставляет ли драйвер параметрNULL или параметр NULLRequest. Например, можно использовать параметр RequestOptions для указания значения времени ожидания.

  2. Предоставьте буферное пространство для параметра WdfUsbTargetDeviceSendControlTransferSynchronous метода MemoryDescriptor.

    Драйвер может указать это буферное пространство в качестве локально выделенного буфера, как дескриптор WDFMEMORY или как MDL. Вы можете использовать любой метод, наиболее удобный.

    При необходимости платформа преобразует описание буфера в то, что правильно для метода целевого объекта ввода-вывода для доступа к буферам данных.

    Доступны следующие методы:

    • Укажите локальный буфер

      Так как WdfUsbTargetDeviceSendControlTransferSynchronous обрабатывает запросы ввода-вывода синхронно, драйвер может создавать буферы запросов, которые являются локальными для вызывающей подпрограммы, как показано в следующем примере кода.

      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);
      

      Кроме того, драйвер может вызывать WdfRequestRetrieveInputMemory или WdfRequestRetrieveOutputMemory для получения дескриптора в объект памяти платформы, представляющий буфер полученного запроса ввода-вывода, если требуется, чтобы драйвер передал содержимое этого буфера целевому объекту ввода-вывода. Драйвер не должен завершить полученный запрос ввода-вывода, пока новый запрос, который WdfUsbTargetDeviceSendControlTransferSynchronous отправляется в целевой объект ввода-вывода, был удален, повторно использован или переформатирован. (WdfUsbTargetDeviceSendControlTransferSynchronous увеличивает число ссылок объекта памяти. Удаление, повторное использование или переформатирование объекта запроса уменьшает количество ссылок объекта памяти.)

    • Предоставление MDL

      Драйверы могут получать многомерные ключи, связанные с полученным запросом ввода-вывода, вызывая WdfRequestRetrieveInputmMdl или WdfRequestRetrieveOutputmMdl.

Платформа задает флаг USBD_SHORT_TRANSFER_OK во внутреннем URB. Если установить этот флаг, последний пакет передачи данных будет меньше максимального размера пакета.

Сведения о получении сведений о состоянии после завершения запроса ввода-вывода см. в получения сведений о завершении.

Дополнительные сведения о методе WdfUsbTargetDeviceSendControlTransferSynchronous и целевых объектов usb-ввода-вывода см. в целевых объектов USB-ввода-вывода.

Примеры

В следующем примере кода инициализируется структура WDF_USB_CONTROL_SETUP_PACKET, а затем вызывается WdfUsbTargetDeviceSendControlTransferSynchronous для отправки передачи элемента управления для конкретного поставщика.

WDF_USB_CONTROL_SETUP_PACKET  controlSetupPacket;

WDF_USB_CONTROL_SETUP_PACKET_INIT_VENDOR(
                                         &controlSetupPacket,
                                         BmRequestHostToDevice,
                                         BmRequestToDevice,
                                         USBFX2LK_REENUMERATE,
                                         0,
                                         0
                                         );

status = WdfUsbTargetDeviceSendControlTransferSynchronously(
                                         UsbDevice,
                                         WDF_NO_HANDLE,
                                         NULL,
                                         &controlSetupPacket,
                                         NULL,
                                         NULL
                                         );
return status;

Требования

Требование Ценность
целевая платформа Всеобщий
минимальная версия KMDF 1.0
минимальная версия UMDF 2.0
заголовка wdfusb.h (include Wdfusb.h)
библиотеки Wdf01000.sys (KMDF); WUDFx02000.dll (UMDF)
IRQL PASSIVE_LEVEL
правил соответствия DDI DriverCreate(kmdf), KmdfIrql(kmdf), KmdfIrql2(kmdf), KmdfIrqlExplicit(kmdf), RequestForUrbXrb(kmdf) ), SyncReqSend(kmdf), UsbKmdfIrql(kmdf), UsbKmdfIrql2(kmdf), UsbKmdfIrqlExplicit(kmdf)

См. также

WDF_USB_CONTROL_SETUP_PACKET

WDF_USB_CONTROL_SETUP_PACKET_INIT_VENDOR

WdfRequestCancelSentRequest

WdfUsbTargetDeviceFormatRequestForControlTransfer

WdfUsbTargetDeviceSendUrbSynchronous