UfxEndpointCreate 関数 (ufxclient.h)
エンドポイント オブジェクトを作成します。
構文
NTSTATUS UfxEndpointCreate(
[in] UFXDEVICE UfxDevice,
[in, out] PUFXENDPOINT_INIT EndpointInit,
[in, optional] PWDF_OBJECT_ATTRIBUTES Attributes,
[in] PWDF_IO_QUEUE_CONFIG TransferQueueConfig,
[in, optional] PWDF_OBJECT_ATTRIBUTES TransferQueueAttributes,
[in] PWDF_IO_QUEUE_CONFIG CommandQueueConfig,
[in, optional] PWDF_OBJECT_ATTRIBUTES CommandQueueAttributes,
[out] UFXENDPOINT *UfxEndpoint
);
パラメーター
[in] UfxDevice
ドライバーが UfxDeviceCreate を呼び出して作成した UFX デバイス オブジェクトへのハンドル。
[in, out] EndpointInit
EVT_UFX_DEVICE_ENDPOINT_ADDまたはEVT_UFX_DEVICE_DEFAULT_ENDPOINT_ADDの呼び出しで UFX によって渡される不透明な構造体。
[in, optional] Attributes
呼び出し元によって割り当てられた WDF_OBJECT_ATTRIBUTES 構造体へのポインター。 この構造体は、 WDF_OBJECT_ATTRIBUTES_INIT または WDF_OBJECT_ATTRIBUTES_INIT_CONTEXT_TYPEで初期化する必要があります。 このパラメーターは省略可能であり、 WDF_NO_OBJECT_ATTRIBUTESできます。
[in] TransferQueueConfig
構造体に割り当てられた呼び出し元 へのポインター WDF_IO_QUEUE_CONFIG 。 この構造体は 、WDF_IO_QUEUE_CONFIG_INITで初期化する必要があります。
[in, optional] TransferQueueAttributes
呼び出し元によって割り当てられた WDF_OBJECT_ATTRIBUTES 構造体へのポインター。 この構造体は、 WDF_OBJECT_ATTRIBUTES_INIT または WDF_OBJECT_ATTRIBUTES_INIT_CONTEXT_TYPEで初期化する必要があります。 このパラメーターは省略可能であり、 WDF_NO_OBJECT_ATTRIBUTESできます。
[in] CommandQueueConfig
構造体に割り当てられた呼び出し元 へのポインター WDF_IO_QUEUE_CONFIG 。 この構造体は 、WDF_IO_QUEUE_CONFIG_INITで初期化する必要があります。
[in, optional] CommandQueueAttributes
呼び出し元によって割り当てられた WDF_OBJECT_ATTRIBUTES 構造体へのポインター。 この構造体は、 WDF_OBJECT_ATTRIBUTES_INIT または WDF_OBJECT_ATTRIBUTES_INIT_CONTEXT_TYPEで初期化する必要があります。 このパラメーターは省略可能であり、 WDF_NO_OBJECT_ATTRIBUTESできます。
[out] UfxEndpoint
UFXENDPOINT オブジェクトへのハンドルを受け取る場所へのポインター。
戻り値
操作が成功した場合、メソッドは STATUS_SUCCESS、または NT_SUCCESS(status) が TRUE である別の状態値を返します。 それ以外の場合は、NT_SUCCESS(status) が FALSE である状態値を返します。
注釈
転送キューは、エンドポイント転送に関連する次の IOCTL を処理します。
- IOCTL_INTERNAL_USBFN_CONTROL_STATUS_HANDSHAKE_IN
- IOCTL_INTERNAL_USBFN_CONTROL_STATUS_HANDSHAKE_OUT
- IOCTL_INTERNAL_USBFN_TRANSFER_IN
- IOCTL_INTERNAL_USBFN_TRANSFER_IN_APPEND_ZERO_PKT
- IOCTL_INTERNAL_USBFN_TRANSFER_OUT
コマンド キューは、次の IOCTL を処理します。
- IOCTL_INTERNAL_USBFN_GET_PIPE_STATE
- IOCTL_INTERNAL_USBFN_SET_PIPE_STATE
- IOCTL_INTERNAL_USBFN_DESCRIPTOR_UPDATE
NTSTATUS
UfxEndpointAdd (
_In_ UFXDEVICE Device,
_In_ PUSB_ENDPOINT_DESCRIPTOR Descriptor,
_Inout_ PUFXENDPOINT_INIT EndpointInit
)
/*++
Routine Description:
Creates a UFXENDPOINT object, and initializes its contexts.
Parameters Description:
Device - UFXDEVICE associated with the endpoint.
Descriptor - Endpoint descriptor for this endpoint.
EndpointInit - Opaque structure from UFX.
Return Value:
STATUS_SUCCESS if successful, appropriate NTSTATUS message otherwise.
--*/
{
NTSTATUS Status;
WDF_OBJECT_ATTRIBUTES Attributes;
WDF_IO_QUEUE_CONFIG TransferQueueConfig;
WDF_OBJECT_ATTRIBUTES TransferQueueAttributes;
WDF_IO_QUEUE_CONFIG CommandQueueConfig;
WDF_OBJECT_ATTRIBUTES CommandQueueAttributes;
UFXENDPOINT Endpoint;
PUFXENDPOINT_CONTEXT EpContext;
PUFXDEVICE_CONTEXT DeviceContext;
UFX_ENDPOINT_CALLBACKS Callbacks;
PENDPOINT_QUEUE_CONTEXT QueueContext;
WDFQUEUE Queue;
TraceEntry();
DeviceContext = UfxDeviceGetContext(Device);
WDF_OBJECT_ATTRIBUTES_INIT_CONTEXT_TYPE(&Attributes, UFXENDPOINT_CONTEXT);
Attributes.ExecutionLevel = WdfExecutionLevelPassive;
Attributes.EvtCleanupCallback = UfxEndpoint_Cleanup;
//
// Note: Execution level needs to be passive to avoid deadlocks with WdfRequestComplete.
//
WDF_OBJECT_ATTRIBUTES_INIT_CONTEXT_TYPE(&TransferQueueAttributes, ENDPOINT_QUEUE_CONTEXT);
TransferQueueAttributes.ExecutionLevel = WdfExecutionLevelPassive;
WDF_IO_QUEUE_CONFIG_INIT(&TransferQueueConfig, WdfIoQueueDispatchManual);
TransferQueueConfig.AllowZeroLengthRequests = TRUE;
TransferQueueConfig.EvtIoStop = EndpointQueue_EvtIoStop;
WDF_OBJECT_ATTRIBUTES_INIT_CONTEXT_TYPE(&CommandQueueAttributes, ENDPOINT_QUEUE_CONTEXT);
CommandQueueAttributes.ExecutionLevel = WdfExecutionLevelPassive;
WDF_IO_QUEUE_CONFIG_INIT(&CommandQueueConfig, WdfIoQueueDispatchSequential);
CommandQueueConfig.EvtIoInternalDeviceControl = EvtEndpointCommandQueue;
UFX_ENDPOINT_CALLBACKS_INIT(&Callbacks);
UfxEndpointInitSetEventCallbacks(EndpointInit, &Callbacks);
Status = UfxEndpointCreate(
Device,
EndpointInit,
&Attributes,
&TransferQueueConfig,
&TransferQueueAttributes,
&CommandQueueConfig,
&CommandQueueAttributes,
&Endpoint);
CHK_NT_MSG(Status, "Failed to create ufxendpoint!");
Status = WdfCollectionAdd(DeviceContext->Endpoints, Endpoint);
CHK_NT_MSG(Status, "Failed to add endpoint to collection!");
EpContext = UfxEndpointGetContext(Endpoint);
EpContext->UfxDevice = Device;
EpContext->WdfDevice = DeviceContext->FdoWdfDevice;
RtlCopyMemory(&EpContext->Descriptor, Descriptor, sizeof(*Descriptor));
Queue = UfxEndpointGetTransferQueue(Endpoint);
QueueContext = EndpointQueueGetContext(Queue);
QueueContext->Endpoint = Endpoint;
Queue = UfxEndpointGetCommandQueue(Endpoint);
QueueContext = EndpointQueueGetContext(Queue);
QueueContext->Endpoint = Endpoint;
Status = TransferInitialize(Endpoint);
CHK_NT_MSG(Status, "Failed to initialize endpoint transfers");
//
// This can happen if we're handling a SetInterface command.
//
if (DeviceContext->UsbState == UsbfnDeviceStateConfigured) {
UfxEndpointConfigure(Endpoint);
}
Status = WdfIoQueueReadyNotify(
UfxEndpointGetTransferQueue(Endpoint),
TransferReadyNotify,
Endpoint);
CHK_NT_MSG(Status, "Failed to register ready notify");
End:
TraceExit();
return Status;
}
要件
要件 | 値 |
---|---|
サポートされている最小のクライアント | Windows 10 |
対象プラットフォーム | Windows |
ヘッダー | ufxclient.h |
Library | ufxstub.lib |
IRQL | PASSIVE_LEVEL |