NTSTATUS
kmdf1394_SubmitIrpSynch (
                         IN WDFIOTARGET IoTarget,
                         IN WDFREQUEST Request,
                         IN PIRB Irb)
/*++

Routine Description:

    Synchronous Irp submission routine

Arguments:

    IoTarget - pointer to the IoTarget object.

    Request - the WDF Request packet to use

    Irb - 1394 I/O Request Block to submit

Return Value:

    NTSTATUS value
--*/
{
    NTSTATUS ntStatus = STATUS_SUCCESS;

    WDF_REQUEST_SEND_OPTIONS option;
    WDF_MEMORY_DESCRIPTOR descriptor;

    UNREFERENCED_PARAMETER (Request);

    ENTER ("kmdf1394_SubmitIrpSynch");

    ASSERT (KeGetCurrentIrql() < DISPATCH_LEVEL);
    ASSERT (Irb);

    WDF_REQUEST_SEND_OPTIONS_INIT (&option, WDF_REQUEST_SEND_OPTION_SYNCHRONOUS);

    WDF_MEMORY_DESCRIPTOR_INIT_BUFFER (&descriptor, Irb, sizeof (IRB));

    ntStatus = WdfIoTargetSendInternalIoctlOthersSynchronously (
        IoTarget, 
        NULL, 
        IOCTL_1394_CLASS, 
        &descriptor, 
        NULL, 
        NULL, 
        &option, 
        NULL);
    if (!NT_SUCCESS(ntStatus)) 
    {
        TRACE(TL_ERROR, ("WdfIoTargetSendInternalIoctlSynchronously " 
            "Failed with status %x\n",ntStatus));
    }

    EXIT ("kmdf1394_SubmitIrpSynch", ntStatus);

    return ntStatus;
} //kmdf1394_SubmitIrpSynch
Beispiel #2
0
VOID
Rio500_EvtIoDeviceControl(
  _In_ WDFQUEUE   Queue,
  _In_ WDFREQUEST Request,
  _In_ size_t     OutputBufferLength,
  _In_ size_t     InputBufferLength,
  _In_ ULONG      IoControlCode
)
/*++

Routine Description:

    This event is called when the framework receives IRP_MJ_DEVICE_CONTROL
    requests from the system.

Arguments:

    Queue - Handle to the framework queue object that is associated
            with the I/O request.
    Request - Handle to a framework request object.

    OutputBufferLength - length of the request's output buffer,
                        if an output buffer is available.
    InputBufferLength - length of the request's input buffer,
                        if an input buffer is available.

    IoControlCode - the driver-defined or system-defined I/O control code
                    (IOCTL) that is associated with the request.
Return Value:

    VOID

--*/
{
  WDFDEVICE             device;
  PVOID                 ioBuffer;
  PRIO_IOCTL_BLOCK      ioBufferRio;
  size_t                bufLength;
  NTSTATUS              status;
  PDEVICE_CONTEXT       pDevContext;
  ULONG                 length = 0;
  URB                   urb;
  PMDL                  pMdl = NULL;
  WDF_MEMORY_DESCRIPTOR memoryDesc;
#ifdef _WIN64
  BOOLEAN               isWowRequest = FALSE;
#endif // _WIN64

  UNREFERENCED_PARAMETER(OutputBufferLength);
  UNREFERENCED_PARAMETER(InputBufferLength);

  Rio500_DbgPrint(3, ("Entered Rio500_DispatchDevCtrl\n"));

  PAGED_CODE();

  //
  // initialize variables
  //
  device = WdfIoQueueGetDevice(Queue);
  pDevContext = GetDeviceContext(device);

  switch(IoControlCode) {
    case IOCTL_RIO500_RESET_PIPE:
      status = ResetPipe(pDevContext->ReadPipe);
      if (NT_SUCCESS(status)) {
        status = ResetPipe(pDevContext->WritePipe);
      }
      break;

    case IOCTL_RIO500_GET_CONFIG_DESCRIPTOR:
      if (pDevContext->UsbConfigurationDescriptor) {
        length = pDevContext->UsbConfigurationDescriptor->wTotalLength;

        status = WdfRequestRetrieveOutputBuffer(Request, length, &ioBuffer, &bufLength);
        if (!NT_SUCCESS(status)) {
          Rio500_DbgPrint(1, ("WdfRequestRetrieveInputBuffer failed\n"));
          break;
        }

        RtlCopyMemory(ioBuffer, pDevContext->UsbConfigurationDescriptor, length);
        status = STATUS_SUCCESS;
      } else {
        status = STATUS_INVALID_DEVICE_STATE;
      }
      break;

    case IOCTL_RIO500_RESET_DEVICE:
      status = ResetDevice(device);
      break;

    case IOCTL_RIO500_RIO_COMMAND:
#ifdef _WIN64
      if (IoIs32bitProcess(NULL)) {
        bufLength = sizeof(RIO_IOCTL_BLOCK) - sizeof(DWORD32);
        isWowRequest = TRUE;
      } else
#endif // _WIN64
      {
        bufLength = sizeof(RIO_IOCTL_BLOCK);
      }
      status = WdfRequestRetrieveInputBuffer(
        Request,
        bufLength,
        &ioBufferRio,
        NULL
      );

      if (NT_SUCCESS(status)) {
#ifdef _WIN64
        if (isWowRequest) {
          ioBuffer = (PVOID)ioBufferRio->MsgData.DataWow;
        } else
#endif // _WIN64
        {
          ioBuffer = ioBufferRio->MsgData.Data;
        }
        if (ioBufferRio->MsgLength != 0 && ioBuffer != NULL) {
          pMdl = IoAllocateMdl(
            ioBuffer,
            ioBufferRio->MsgLength,
            FALSE,
            FALSE,
            NULL
          );
          MmProbeAndLockPages(pMdl, (KPROCESSOR_MODE)KernelMode, IoModifyAccess);
        }

        memset(&urb, 0, sizeof(urb));
        urb.UrbControlVendorClassRequest.Hdr.Length = sizeof(struct _URB_CONTROL_VENDOR_OR_CLASS_REQUEST);
        urb.UrbControlVendorClassRequest.Hdr.Function = URB_FUNCTION_VENDOR_DEVICE;
        urb.UrbControlVendorClassRequest.TransferBuffer = NULL;
        urb.UrbControlVendorClassRequest.RequestTypeReservedBits = 0x00;
        urb.UrbControlVendorClassRequest.TransferBufferLength = ioBufferRio->MsgLength;
        urb.UrbControlVendorClassRequest.TransferBufferMDL = pMdl;
        urb.UrbControlVendorClassRequest.Request = ioBufferRio->RequestCode;
        urb.UrbControlVendorClassRequest.Value = ioBufferRio->MsgValue;
        urb.UrbControlVendorClassRequest.Index = ioBufferRio->MsgIndex;
        urb.UrbControlVendorClassRequest.TransferFlags = USBD_SHORT_TRANSFER_OK;
        if (ioBufferRio->RequestType & 0x80) {
          urb.UrbControlVendorClassRequest.TransferFlags |= USBD_TRANSFER_DIRECTION_IN;
        }
        urb.UrbControlVendorClassRequest.UrbLink = NULL;
      
        WDF_MEMORY_DESCRIPTOR_INIT_BUFFER(&memoryDesc, &urb, sizeof(urb));
        status = WdfIoTargetSendInternalIoctlOthersSynchronously(
          WdfDeviceGetIoTarget(device),
          Request,
          IOCTL_INTERNAL_USB_SUBMIT_URB,
          &memoryDesc,
          NULL,
          NULL,
          NULL,
          NULL
        );

        if (pMdl != NULL) {
          MmUnlockPages(pMdl);
          IoFreeMdl(pMdl);
        }
      }
      break;

    default:
      status = STATUS_INVALID_DEVICE_REQUEST;
      break;
  }

  WdfRequestCompleteWithInformation(Request, status, length);

  Rio500_DbgPrint(3, ("Exit Rio500_DispatchDevCtrl\n"));
}
Beispiel #3
0
NTSTATUS
FORCEINLINE
BthEchoSharedSendBrbSynchronously(
    _In_ WDFIOTARGET IoTarget,
    _In_ WDFREQUEST Request,
    _In_ PBRB Brb,
    _In_ ULONG BrbSize
)
/*++

Routine Description:

    This routine formats a request with brb and sends it synchronously

Arguments:

    IoTarget - Target to send the brb to
    Request - request object to be formatted with brb
    Brb - Brb to be sent
    BrbSize - size of the Brb data structure

Return Value:

    NTSTATUS Status code.

Notes:

    This routine does calls WdfRequestReuse on the Request passed in.
    Caller need not do so before passing in the request.

    This routine does not complete the request in case of failure.
    Caller must complete the request in case of failure.

--*/
{
    NTSTATUS status;
    WDF_REQUEST_REUSE_PARAMS reuseParams;
    WDF_MEMORY_DESCRIPTOR OtherArg1Desc;

    WDF_REQUEST_REUSE_PARAMS_INIT(
        &reuseParams,
        WDF_REQUEST_REUSE_NO_FLAGS,
        STATUS_NOT_SUPPORTED
    );

    status = WdfRequestReuse(Request, &reuseParams);
    if (!NT_SUCCESS(status))
    {
        goto exit;
    }

    WDF_MEMORY_DESCRIPTOR_INIT_BUFFER(
        &OtherArg1Desc,
        Brb,
        BrbSize
    );

    status = WdfIoTargetSendInternalIoctlOthersSynchronously(
                 IoTarget,
                 Request,
                 IOCTL_INTERNAL_BTH_SUBMIT_BRB,
                 &OtherArg1Desc,
                 NULL, //OtherArg2
                 NULL, //OtherArg4
                 NULL, //RequestOptions
                 NULL  //BytesReturned
             );

exit:
    return status;
}