2 * PROJECT: ReactOS Universal Serial Bus Human Interface Device Driver
3 * LICENSE: GPL - See COPYING in the top level directory
4 * FILE: drivers/usb/hidusb/hidusb.c
5 * PURPOSE: HID USB Interface Driver
7 * Michael Martin (michael.martin@reactos.org)
8 * Johannes Anderwald (johannes.anderwald@reactos.org)
13 PUSBD_PIPE_INFORMATION
14 HidUsb_GetInputInterruptInterfaceHandle(
15 PUSBD_INTERFACE_INFORMATION InterfaceInformation
)
22 ASSERT(InterfaceInformation
->NumberOfPipes
);
24 for(Index
= 0; Index
< InterfaceInformation
->NumberOfPipes
; Index
++)
26 //DPRINT1("[HIDUSB] EndpointAddress %x PipeType %x PipeHandle %x\n", InterfaceInformation->Pipes[Index].EndpointAddress, InterfaceInformation->Pipes[Index].PipeType, InterfaceInformation->Pipes[Index].PipeHandle);
27 if (InterfaceInformation
->Pipes
[Index
].PipeType
== UsbdPipeTypeInterrupt
&& (InterfaceInformation
->Pipes
[Index
].EndpointAddress
& USB_ENDPOINT_DIRECTION_MASK
))
32 return &InterfaceInformation
->Pipes
[Index
];
44 IN PDEVICE_OBJECT DeviceObject
,
49 IO_STATUS_BLOCK IoStatus
;
50 PHID_DEVICE_EXTENSION DeviceExtension
;
51 PIO_STACK_LOCATION IoStack
;
55 // get device extension
57 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
67 KeInitializeEvent(&Event
, NotificationEvent
, FALSE
);
72 Irp
= IoBuildDeviceIoControlRequest(IOCTL_INTERNAL_USB_GET_PORT_STATUS
, DeviceExtension
->NextDeviceObject
, NULL
, 0, NULL
, 0, TRUE
, &Event
, &IoStatus
);
78 return STATUS_INSUFFICIENT_RESOURCES
;
84 IoStack
= IoGetNextIrpStackLocation(Irp
);
87 // store result buffer
89 IoStack
->Parameters
.Others
.Argument1
= (PVOID
)PortStatus
;
94 Status
= IoCallDriver(DeviceExtension
->NextDeviceObject
, Irp
);
95 if (Status
== STATUS_PENDING
)
98 // wait for completion
100 KeWaitForSingleObject(&Event
, Executive
, KernelMode
, 0, NULL
);
101 return IoStatus
.Status
;
111 HidUsb_ResetInterruptPipe(
112 IN PDEVICE_OBJECT DeviceObject
)
114 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
115 PHID_DEVICE_EXTENSION DeviceExtension
;
116 PUSBD_PIPE_INFORMATION PipeInformation
;
121 // get device extension
123 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
124 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
127 // get interrupt pipe handle
129 ASSERT(HidDeviceExtension
->InterfaceInfo
);
130 PipeInformation
= HidUsb_GetInputInterruptInterfaceHandle(HidDeviceExtension
->InterfaceInfo
);
131 ASSERT(PipeInformation
);
132 ASSERT(PipeInformation
->PipeHandle
);
137 Urb
= ExAllocatePool(NonPagedPool
, sizeof(struct _URB_PIPE_REQUEST
));
143 return STATUS_INSUFFICIENT_RESOURCES
;
149 RtlZeroMemory(Urb
, sizeof(struct _URB_PIPE_REQUEST
));
150 Urb
->UrbHeader
.Function
= URB_FUNCTION_SYNC_RESET_PIPE_AND_CLEAR_STALL
;
151 Urb
->UrbHeader
.Length
= sizeof(struct _URB_PIPE_REQUEST
);
152 Urb
->UrbPipeRequest
.PipeHandle
= PipeInformation
->PipeHandle
;
157 Status
= Hid_DispatchUrb(DeviceObject
, Urb
);
172 IN PDEVICE_OBJECT DeviceObject
)
174 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
175 PHID_DEVICE_EXTENSION DeviceExtension
;
178 PUSBD_PIPE_INFORMATION PipeInformation
;
181 // get device extension
183 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
184 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
189 Urb
= ExAllocatePool(NonPagedPool
, sizeof(struct _URB_PIPE_REQUEST
));
195 return STATUS_INSUFFICIENT_RESOURCES
;
199 // get pipe information
201 PipeInformation
= HidUsb_GetInputInterruptInterfaceHandle(HidDeviceExtension
->InterfaceInfo
);
202 ASSERT(PipeInformation
);
203 ASSERT(PipeInformation
->PipeHandle
);
208 RtlZeroMemory(Urb
, sizeof(struct _URB_PIPE_REQUEST
));
209 Urb
->UrbHeader
.Function
= URB_FUNCTION_ABORT_PIPE
;
210 Urb
->UrbHeader
.Length
= sizeof(struct _URB_PIPE_REQUEST
);
211 Urb
->UrbPipeRequest
.PipeHandle
= PipeInformation
->PipeHandle
;
216 Status
= Hid_DispatchUrb(DeviceObject
, Urb
);
231 IN PDEVICE_OBJECT DeviceObject
)
235 PHID_DEVICE_EXTENSION DeviceExtension
;
236 IO_STATUS_BLOCK IoStatusBlock
;
240 // get device extension
242 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
247 KeInitializeEvent(&Event
, NotificationEvent
, FALSE
);
252 Irp
= IoBuildDeviceIoControlRequest(IOCTL_INTERNAL_USB_RESET_PORT
, DeviceExtension
->NextDeviceObject
, NULL
, 0, NULL
, 0, TRUE
, &Event
, &IoStatusBlock
);
258 return STATUS_INSUFFICIENT_RESOURCES
;
264 Status
= IoCallDriver(DeviceExtension
->NextDeviceObject
, Irp
);
265 if (Status
== STATUS_PENDING
)
268 // wait for request completion
270 KeWaitForSingleObject(&Event
, Executive
, KernelMode
, FALSE
, NULL
);
271 Status
= IoStatusBlock
.Status
;
277 return IoStatusBlock
.Status
;
283 IN PDEVICE_OBJECT DeviceObject
,
286 PIO_STACK_LOCATION IoStack
;
289 // get current irp stack location
291 IoStack
= IoGetCurrentIrpStackLocation(Irp
);
294 // sanity check for hidclass driver
296 ASSERT(IoStack
->MajorFunction
== IRP_MJ_CREATE
|| IoStack
->MajorFunction
== IRP_MJ_CLOSE
);
301 Irp
->IoStatus
.Information
= 0;
302 Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
303 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
306 // informal debug print
308 DPRINT("HIDUSB Request: %x\n", IoStack
->MajorFunction
);
313 return STATUS_SUCCESS
;
318 HidUsb_ResetWorkerRoutine(
319 IN PDEVICE_OBJECT DeviceObject
,
324 PHID_USB_RESET_CONTEXT ResetContext
;
325 PHID_DEVICE_EXTENSION DeviceExtension
;
327 DPRINT("[HIDUSB] ResetWorkerRoutine\n");
332 ResetContext
= (PHID_USB_RESET_CONTEXT
)Ctx
;
335 // get device extension
337 DeviceExtension
= (PHID_DEVICE_EXTENSION
)ResetContext
->DeviceObject
->DeviceExtension
;
342 Status
= HidUsb_GetPortStatus(ResetContext
->DeviceObject
, &PortStatus
);
343 DPRINT("[HIDUSB] ResetWorkerRoutine GetPortStatus %x PortStatus %x\n", Status
, PortStatus
);
344 if (NT_SUCCESS(Status
))
346 if (!(PortStatus
& USB_PORT_STATUS_ENABLE
))
351 Status
= HidUsb_ResetInterruptPipe(ResetContext
->DeviceObject
);
352 DPRINT1("[HIDUSB] ResetWorkerRoutine ResetPipe %x\n", Status
);
359 Status
= HidUsb_AbortPipe(ResetContext
->DeviceObject
);
360 DPRINT1("[HIDUSB] ResetWorkerRoutine AbortPipe %x\n", Status
);
361 if (NT_SUCCESS(Status
))
366 Status
= HidUsb_ResetPort(ResetContext
->DeviceObject
);
367 DPRINT1("[HIDUSB] ResetPort %x\n", Status
);
368 if (Status
== STATUS_DEVICE_DATA_ERROR
)
371 // invalidate device state
373 IoInvalidateDeviceState(DeviceExtension
->PhysicalDeviceObject
);
377 // reset interrupt pipe
379 if (NT_SUCCESS(Status
))
384 Status
= HidUsb_ResetInterruptPipe(ResetContext
->DeviceObject
);
385 DPRINT1("[HIDUSB] ResetWorkerRoutine ResetPipe %x\n", Status
);
394 ASSERT(KeGetCurrentIrql() == PASSIVE_LEVEL
);
395 IoFreeWorkItem(ResetContext
->WorkItem
);
396 IoCompleteRequest(ResetContext
->Irp
, IO_NO_INCREMENT
);
397 ExFreePool(ResetContext
);
403 HidUsb_ReadReportCompletion(
404 IN PDEVICE_OBJECT DeviceObject
,
408 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
409 PHID_DEVICE_EXTENSION DeviceExtension
;
411 PHID_USB_RESET_CONTEXT ResetContext
;
419 DPRINT("[HIDUSB] HidUsb_ReadReportCompletion %p Status %x Urb Status %x\n", Irp
, Irp
->IoStatus
, Urb
->UrbHeader
.Status
);
421 if (Irp
->PendingReturned
)
426 IoMarkIrpPending(Irp
);
430 // did the reading report succeed / cancelled
432 if (NT_SUCCESS(Irp
->IoStatus
.Status
) || Irp
->IoStatus
.Status
== STATUS_CANCELLED
|| Irp
->IoStatus
.Status
== STATUS_DEVICE_NOT_CONNECTED
)
435 // store result length
437 Irp
->IoStatus
.Information
= Urb
->UrbBulkOrInterruptTransfer
.TransferBufferLength
;
440 // FIXME handle error
442 ASSERT(Urb
->UrbHeader
.Status
== USBD_STATUS_SUCCESS
);
452 return STATUS_CONTINUE_COMPLETION
;
456 // get device extension
458 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
459 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
462 // allocate reset context
464 ResetContext
= (PHID_USB_RESET_CONTEXT
)ExAllocatePool(NonPagedPool
, sizeof(HID_USB_RESET_CONTEXT
));
468 // allocate work item
470 ResetContext
->WorkItem
= IoAllocateWorkItem(DeviceObject
);
471 if (ResetContext
->WorkItem
)
474 // init reset context
476 ResetContext
->Irp
= Irp
;
477 ResetContext
->DeviceObject
= DeviceObject
;
480 // queue the work item
482 IoQueueWorkItem(ResetContext
->WorkItem
, HidUsb_ResetWorkerRoutine
, DelayedWorkQueue
, ResetContext
);
492 return STATUS_MORE_PROCESSING_REQUIRED
;
497 ExFreePool(ResetContext
);
508 return STATUS_CONTINUE_COMPLETION
;
515 IN PDEVICE_OBJECT DeviceObject
,
518 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
519 PHID_DEVICE_EXTENSION DeviceExtension
;
520 PIO_STACK_LOCATION IoStack
;
522 PUSBD_PIPE_INFORMATION PipeInformation
;
525 // get device extension
527 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
528 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
531 // get current stack location
533 IoStack
= IoGetCurrentIrpStackLocation(Irp
);
538 ASSERT(IoStack
->Parameters
.DeviceIoControl
.OutputBufferLength
);
539 ASSERT(Irp
->UserBuffer
);
540 ASSERT(HidDeviceExtension
->InterfaceInfo
);
543 // get interrupt input pipe
545 PipeInformation
= HidUsb_GetInputInterruptInterfaceHandle(HidDeviceExtension
->InterfaceInfo
);
546 ASSERT(PipeInformation
);
551 Urb
= (PURB
)ExAllocatePool(NonPagedPool
, sizeof(struct _URB_BULK_OR_INTERRUPT_TRANSFER
));
557 return STATUS_INSUFFICIENT_RESOURCES
;
563 RtlZeroMemory(Urb
, sizeof(struct _URB_BULK_OR_INTERRUPT_TRANSFER
));
568 ASSERT(Irp
->UserBuffer
);
569 ASSERT(IoStack
->Parameters
.DeviceIoControl
.OutputBufferLength
);
570 ASSERT(PipeInformation
->PipeHandle
);
575 UsbBuildInterruptOrBulkTransferRequest(Urb
,
576 sizeof(struct _URB_BULK_OR_INTERRUPT_TRANSFER
),
577 PipeInformation
->PipeHandle
,
580 IoStack
->Parameters
.DeviceIoControl
.OutputBufferLength
,
581 USBD_TRANSFER_DIRECTION_IN
| USBD_SHORT_TRANSFER_OK
,
585 // store configuration handle
587 Urb
->UrbHeader
.UsbdDeviceHandle
= HidDeviceExtension
->ConfigurationHandle
;
590 // get next location to setup irp
592 IoStack
= IoGetNextIrpStackLocation(Irp
);
595 // init irp for lower driver
597 IoStack
->MajorFunction
= IRP_MJ_INTERNAL_DEVICE_CONTROL
;
598 IoStack
->Parameters
.DeviceIoControl
.IoControlCode
= IOCTL_INTERNAL_USB_SUBMIT_URB
;
599 IoStack
->Parameters
.DeviceIoControl
.InputBufferLength
= 0;
600 IoStack
->Parameters
.DeviceIoControl
.OutputBufferLength
= 0;
601 IoStack
->Parameters
.DeviceIoControl
.Type3InputBuffer
= NULL
;
602 IoStack
->Parameters
.Others
.Argument1
= (PVOID
)Urb
;
606 // set completion routine
608 IoSetCompletionRoutine(Irp
, HidUsb_ReadReportCompletion
, (PVOID
)Urb
, TRUE
, TRUE
, TRUE
);
613 return IoCallDriver(DeviceExtension
->NextDeviceObject
, Irp
);
619 HidUsb_GetReportDescriptor(
620 IN PDEVICE_OBJECT DeviceObject
,
623 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
624 PHID_DEVICE_EXTENSION DeviceExtension
;
626 ULONG BufferLength
, Length
;
627 PIO_STACK_LOCATION IoStack
;
631 // get device extension
633 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
634 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
639 ASSERT(HidDeviceExtension
);
640 ASSERT(HidDeviceExtension
->HidDescriptor
);
641 ASSERT(HidDeviceExtension
->HidDescriptor
->bNumDescriptors
>= 1);
642 ASSERT(HidDeviceExtension
->HidDescriptor
->DescriptorList
[0].bReportType
== HID_REPORT_DESCRIPTOR_TYPE
);
643 ASSERT(HidDeviceExtension
->HidDescriptor
->DescriptorList
[0].wReportLength
> 0);
646 // FIXME: support old hid version
648 BufferLength
= HidDeviceExtension
->HidDescriptor
->DescriptorList
[0].wReportLength
;
649 Status
= Hid_GetDescriptor(DeviceObject
, URB_FUNCTION_GET_DESCRIPTOR_FROM_INTERFACE
, sizeof(struct _URB_CONTROL_DESCRIPTOR_REQUEST
), &Report
, &BufferLength
, HidDeviceExtension
->HidDescriptor
->DescriptorList
[0].bReportType
, 0, HidDeviceExtension
->InterfaceInfo
->InterfaceNumber
);
650 if (!NT_SUCCESS(Status
))
653 // failed to get descriptor
655 DPRINT("[HIDUSB] failed to get report descriptor with %x\n", Status
);
661 // get current stack location
663 IoStack
= IoGetCurrentIrpStackLocation(Irp
);
664 DPRINT("[HIDUSB] GetReportDescriptor: Status %x ReportLength %lu OutputBufferLength %lu TransferredLength %lu\n", Status
, HidDeviceExtension
->HidDescriptor
->DescriptorList
[0].wReportLength
, IoStack
->Parameters
.DeviceIoControl
.OutputBufferLength
, BufferLength
);
667 // get length to copy
669 Length
= min(IoStack
->Parameters
.DeviceIoControl
.OutputBufferLength
, BufferLength
);
675 RtlCopyMemory(Irp
->UserBuffer
, Report
, Length
);
678 // store result length
680 Irp
->IoStatus
.Information
= Length
;
691 HidInternalDeviceControl(
692 IN PDEVICE_OBJECT DeviceObject
,
695 PIO_STACK_LOCATION IoStack
;
696 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
697 PHID_DEVICE_EXTENSION DeviceExtension
;
698 PHID_DEVICE_ATTRIBUTES Attributes
;
703 // get device extension
705 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
706 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
709 // get current stack location
711 IoStack
= IoGetCurrentIrpStackLocation(Irp
);
713 switch(IoStack
->Parameters
.DeviceIoControl
.IoControlCode
)
715 case IOCTL_HID_GET_DEVICE_ATTRIBUTES
:
717 if (IoStack
->Parameters
.DeviceIoControl
.OutputBufferLength
< sizeof(HID_DEVICE_ATTRIBUTES
))
722 Irp
->IoStatus
.Status
= STATUS_INVALID_BUFFER_SIZE
;
723 DPRINT1("[HIDUSB] IOCTL_HID_GET_DEVICE_ATTRIBUTES invalid buffer\n");
724 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
725 return STATUS_INVALID_BUFFER_SIZE
;
730 DPRINT("[HIDUSB] IOCTL_HID_GET_DEVICE_ATTRIBUTES\n");
731 ASSERT(HidDeviceExtension
->DeviceDescriptor
);
732 Irp
->IoStatus
.Information
= sizeof(HID_DESCRIPTOR
);
733 Attributes
= (PHID_DEVICE_ATTRIBUTES
)Irp
->UserBuffer
;
734 Attributes
->Size
= sizeof(HID_DEVICE_ATTRIBUTES
);
735 Attributes
->VendorID
= HidDeviceExtension
->DeviceDescriptor
->idVendor
;
736 Attributes
->ProductID
= HidDeviceExtension
->DeviceDescriptor
->idProduct
;
737 Attributes
->VersionNumber
= HidDeviceExtension
->DeviceDescriptor
->bcdDevice
;
742 Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
743 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
744 return STATUS_SUCCESS
;
746 case IOCTL_HID_GET_DEVICE_DESCRIPTOR
:
751 ASSERT(HidDeviceExtension
->HidDescriptor
);
752 DPRINT("[HIDUSB] IOCTL_HID_GET_DEVICE_DESCRIPTOR DescriptorLength %lu OutputBufferLength %lu\n", HidDeviceExtension
->HidDescriptor
->bLength
, IoStack
->Parameters
.DeviceIoControl
.OutputBufferLength
);
757 Length
= min(HidDeviceExtension
->HidDescriptor
->bLength
, IoStack
->Parameters
.DeviceIoControl
.OutputBufferLength
);
762 RtlCopyMemory(Irp
->UserBuffer
, HidDeviceExtension
->HidDescriptor
, Length
);
765 // store result length
767 Irp
->IoStatus
.Information
= HidDeviceExtension
->HidDescriptor
->bLength
;
768 Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
770 /* complete request */
771 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
772 return STATUS_SUCCESS
;
774 case IOCTL_HID_GET_REPORT_DESCRIPTOR
:
776 Status
= HidUsb_GetReportDescriptor(DeviceObject
, Irp
);
777 DPRINT("[HIDUSB] IOCTL_HID_GET_REPORT_DESCRIPTOR Status %x\n", Status
);
778 Irp
->IoStatus
.Status
= Status
;
779 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
782 case IOCTL_HID_READ_REPORT
:
784 DPRINT("[HIDUSB] IOCTL_HID_READ_REPORT\n");
785 Status
= HidUsb_ReadReport(DeviceObject
, Irp
);
788 case IOCTL_HID_WRITE_REPORT
:
790 DPRINT1("[HIDUSB] IOCTL_HID_WRITE_REPORT not implemented \n");
792 Irp
->IoStatus
.Status
= STATUS_NOT_IMPLEMENTED
;
793 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
794 return STATUS_NOT_IMPLEMENTED
;
796 case IOCTL_GET_PHYSICAL_DESCRIPTOR
:
798 DPRINT1("[HIDUSB] IOCTL_GET_PHYSICAL_DESCRIPTOR not implemented \n");
800 Irp
->IoStatus
.Status
= STATUS_NOT_IMPLEMENTED
;
801 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
802 return STATUS_NOT_IMPLEMENTED
;
804 case IOCTL_HID_SEND_IDLE_NOTIFICATION_REQUEST
:
806 DPRINT1("[HIDUSB] IOCTL_HID_SEND_IDLE_NOTIFICATION_REQUEST not implemented \n");
808 Irp
->IoStatus
.Status
= STATUS_NOT_IMPLEMENTED
;
809 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
810 return STATUS_NOT_IMPLEMENTED
;
812 case IOCTL_HID_GET_FEATURE
:
814 DPRINT1("[HIDUSB] IOCTL_HID_GET_FEATURE not implemented \n");
816 Irp
->IoStatus
.Status
= STATUS_NOT_IMPLEMENTED
;
817 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
818 return STATUS_NOT_IMPLEMENTED
;
820 case IOCTL_HID_SET_FEATURE
:
822 DPRINT1("[HIDUSB] IOCTL_HID_SET_FEATURE not implemented \n");
824 Irp
->IoStatus
.Status
= STATUS_NOT_IMPLEMENTED
;
825 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
826 return STATUS_NOT_IMPLEMENTED
;
828 case IOCTL_HID_SET_OUTPUT_REPORT
:
830 DPRINT1("[HIDUSB] IOCTL_HID_SET_OUTPUT_REPORT not implemented \n");
832 Irp
->IoStatus
.Status
= STATUS_NOT_IMPLEMENTED
;
833 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
834 return STATUS_NOT_IMPLEMENTED
;
836 case IOCTL_HID_GET_INPUT_REPORT
:
838 DPRINT1("[HIDUSB] IOCTL_HID_GET_INPUT_REPORT not implemented \n");
840 Irp
->IoStatus
.Status
= STATUS_NOT_IMPLEMENTED
;
841 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
842 return STATUS_NOT_IMPLEMENTED
;
844 case IOCTL_HID_GET_INDEXED_STRING
:
846 DPRINT1("[HIDUSB] IOCTL_HID_GET_INDEXED_STRING not implemented \n");
848 Irp
->IoStatus
.Status
= STATUS_NOT_IMPLEMENTED
;
849 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
850 return STATUS_NOT_IMPLEMENTED
;
852 case IOCTL_HID_GET_MS_GENRE_DESCRIPTOR
:
854 DPRINT1("[HIDUSB] IOCTL_HID_GET_MS_GENRE_DESCRIPTOR not implemented \n");
856 Irp
->IoStatus
.Status
= STATUS_NOT_IMPLEMENTED
;
857 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
858 return STATUS_NOT_IMPLEMENTED
;
864 Status
= Irp
->IoStatus
.Status
;
865 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
874 IN PDEVICE_OBJECT DeviceObject
,
879 return STATUS_NOT_IMPLEMENTED
;
885 IN PDEVICE_OBJECT DeviceObject
,
888 PHID_DEVICE_EXTENSION DeviceExtension
;
891 // get hid device extension
893 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
896 // copy stack location
898 IoCopyCurrentIrpStackLocationToNext(Irp
);
903 return IoCallDriver(DeviceExtension
->NextDeviceObject
, Irp
);
909 IN PDEVICE_OBJECT DeviceObject
,
916 KeSetEvent((PRKEVENT
)Context
, 0, FALSE
);
921 return STATUS_MORE_PROCESSING_REQUIRED
;
927 IN PDEVICE_OBJECT DeviceObject
,
932 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
933 PHID_DEVICE_EXTENSION DeviceExtension
;
934 IO_STATUS_BLOCK IoStatus
;
935 PIO_STACK_LOCATION IoStack
;
941 KeInitializeEvent(&Event
, NotificationEvent
, FALSE
);
944 // get device extension
946 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
947 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
953 Irp
= IoBuildDeviceIoControlRequest(IOCTL_INTERNAL_USB_SUBMIT_URB
, DeviceExtension
->NextDeviceObject
, NULL
, 0, NULL
, 0, TRUE
, &Event
, &IoStatus
);
959 return STATUS_INSUFFICIENT_RESOURCES
;
963 // get next stack location
965 IoStack
= IoGetNextIrpStackLocation(Irp
);
970 IoStack
->Parameters
.Others
.Argument1
= (PVOID
)Urb
;
973 // set completion routine
975 IoSetCompletionRoutine(Irp
, Hid_PnpCompletion
, (PVOID
)&Event
, TRUE
, TRUE
, TRUE
);
980 Status
= IoCallDriver(DeviceExtension
->NextDeviceObject
, Irp
);
983 // wait for the request to finish
985 if (Status
== STATUS_PENDING
)
987 KeWaitForSingleObject(&Event
, Executive
, KernelMode
, FALSE
, NULL
);
993 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
995 if (Status
== STATUS_PENDING
)
1000 Status
= IoStatus
.Status
;
1003 DPRINT("[HIDUSB] DispatchUrb %x\n", Status
);
1014 IN PDEVICE_OBJECT DeviceObject
,
1015 IN USHORT UrbFunction
,
1016 IN USHORT UrbLength
,
1017 IN OUT PVOID
*UrbBuffer
,
1018 IN OUT PULONG UrbBufferLength
,
1019 IN UCHAR DescriptorType
,
1021 IN USHORT LanguageIndex
)
1025 UCHAR Allocated
= FALSE
;
1030 Urb
= (PURB
)ExAllocatePool(NonPagedPool
, UrbLength
);
1036 return STATUS_INSUFFICIENT_RESOURCES
;
1040 // is there an urb buffer
1047 *UrbBuffer
= ExAllocatePool(NonPagedPool
, *UrbBufferLength
);
1054 return STATUS_INSUFFICIENT_RESOURCES
;
1060 RtlZeroMemory(*UrbBuffer
, *UrbBufferLength
);
1067 RtlZeroMemory(Urb
, UrbLength
);
1070 // build descriptor request
1072 UsbBuildGetDescriptorRequest(Urb
, UrbLength
, DescriptorType
, Index
, LanguageIndex
, *UrbBuffer
, NULL
, *UrbBufferLength
, NULL
);
1077 Urb
->UrbHeader
.Function
= UrbFunction
;
1082 Status
= Hid_DispatchUrb(DeviceObject
, Urb
);
1085 // did the request fail
1087 if (!NT_SUCCESS(Status
))
1092 // free allocated buffer
1094 ExFreePool(*UrbBuffer
);
1102 *UrbBufferLength
= 0;
1107 // did urb request fail
1109 if (!NT_SUCCESS(Urb
->UrbHeader
.Status
))
1114 // free allocated buffer
1116 ExFreePool(*UrbBuffer
);
1124 *UrbBufferLength
= 0;
1125 return STATUS_UNSUCCESSFUL
;
1129 // store result length
1131 *UrbBufferLength
= Urb
->UrbControlDescriptorRequest
.TransferBufferLength
;
1139 // completed successfully
1141 return STATUS_SUCCESS
;
1145 Hid_SelectConfiguration(
1146 IN PDEVICE_OBJECT DeviceObject
)
1148 PUSB_INTERFACE_DESCRIPTOR InterfaceDescriptor
;
1150 USBD_INTERFACE_LIST_ENTRY InterfaceList
[2];
1152 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
1153 PHID_DEVICE_EXTENSION DeviceExtension
;
1156 // get device extension
1158 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
1159 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
1162 // now parse the descriptors
1164 InterfaceDescriptor
= USBD_ParseConfigurationDescriptorEx(HidDeviceExtension
->ConfigurationDescriptor
,
1165 HidDeviceExtension
->ConfigurationDescriptor
,
1168 USB_DEVICE_CLASS_HUMAN_INTERFACE
,
1175 ASSERT(InterfaceDescriptor
);
1176 ASSERT(InterfaceDescriptor
->bInterfaceClass
== USB_DEVICE_CLASS_HUMAN_INTERFACE
);
1177 ASSERT(InterfaceDescriptor
->bDescriptorType
== USB_INTERFACE_DESCRIPTOR_TYPE
);
1178 ASSERT(InterfaceDescriptor
->bLength
== sizeof(USB_INTERFACE_DESCRIPTOR
));
1181 // setup interface list
1183 RtlZeroMemory(InterfaceList
, sizeof(InterfaceList
));
1184 InterfaceList
[0].InterfaceDescriptor
= InterfaceDescriptor
;
1189 Urb
= USBD_CreateConfigurationRequestEx(HidDeviceExtension
->ConfigurationDescriptor
, InterfaceList
);
1195 return STATUS_INSUFFICIENT_RESOURCES
;
1201 Status
= Hid_DispatchUrb(DeviceObject
, Urb
);
1202 if (NT_SUCCESS(Status
))
1205 // store configuration handle
1207 HidDeviceExtension
->ConfigurationHandle
= Urb
->UrbSelectConfiguration
.ConfigurationHandle
;
1210 // copy interface info
1212 HidDeviceExtension
->InterfaceInfo
= (PUSBD_INTERFACE_INFORMATION
)ExAllocatePool(NonPagedPool
, Urb
->UrbSelectConfiguration
.Interface
.Length
);
1213 if (HidDeviceExtension
->InterfaceInfo
)
1216 // copy interface info
1218 RtlCopyMemory(HidDeviceExtension
->InterfaceInfo
, &Urb
->UrbSelectConfiguration
.Interface
, Urb
->UrbSelectConfiguration
.Interface
.Length
);
1235 IN PDEVICE_OBJECT DeviceObject
)
1237 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
1238 PHID_DEVICE_EXTENSION DeviceExtension
;
1243 // get device extension
1245 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
1246 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
1251 Urb
= ExAllocatePool(NonPagedPool
, sizeof(struct _URB_CONTROL_VENDOR_OR_CLASS_REQUEST
));
1257 return STATUS_INSUFFICIENT_RESOURCES
;
1263 RtlZeroMemory(Urb
, sizeof(struct _URB_CONTROL_VENDOR_OR_CLASS_REQUEST
));
1268 UsbBuildVendorRequest(Urb
,
1269 URB_FUNCTION_CLASS_INTERFACE
,
1270 sizeof(struct _URB_CONTROL_VENDOR_OR_CLASS_REQUEST
),
1273 USB_SET_IDLE_REQUEST
, // HID_SET_IDLE
1284 Status
= Hid_DispatchUrb(DeviceObject
, Urb
);
1294 DPRINT("Status %x\n", Status
);
1301 IN PDEVICE_OBJECT DeviceObject
)
1303 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
1304 PHID_DEVICE_EXTENSION DeviceExtension
;
1310 // get device extension
1312 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
1313 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
1314 ASSERT(HidDeviceExtension
->InterfaceInfo
);
1316 if (HidDeviceExtension
->InterfaceInfo
->SubClass
!= 0x1)
1319 // device does not support the boot protocol
1328 Urb
= ExAllocatePool(NonPagedPool
, sizeof(struct _URB_CONTROL_VENDOR_OR_CLASS_REQUEST
));
1340 RtlZeroMemory(Urb
, sizeof(struct _URB_CONTROL_VENDOR_OR_CLASS_REQUEST
));
1345 UsbBuildVendorRequest(Urb
,
1346 URB_FUNCTION_CLASS_INTERFACE
,
1347 sizeof(struct _URB_CONTROL_VENDOR_OR_CLASS_REQUEST
),
1348 USBD_TRANSFER_DIRECTION_IN
,
1350 USB_GET_PROTOCOL_REQUEST
,
1361 Status
= Hid_DispatchUrb(DeviceObject
, Urb
);
1369 // boot protocol active 0x00 disabled 0x1
1371 if (Protocol
[0] != 0x1)
1373 if (Protocol
[0] == 0x00)
1375 DPRINT1("[HIDUSB] Need to disable boot protocol!\n");
1379 DPRINT1("[HIDUSB] Unexpected protocol value %x\n", Protocol
[0] & 0xFF);
1386 IN PDEVICE_OBJECT DeviceObject
)
1388 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
1389 PHID_DEVICE_EXTENSION DeviceExtension
;
1391 ULONG DescriptorLength
;
1392 PUSB_INTERFACE_DESCRIPTOR InterfaceDescriptor
;
1393 PHID_DESCRIPTOR HidDescriptor
;
1396 // get device extension
1398 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
1399 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
1402 // get device descriptor
1404 DescriptorLength
= sizeof(USB_DEVICE_DESCRIPTOR
);
1405 Status
= Hid_GetDescriptor(DeviceObject
, URB_FUNCTION_GET_DESCRIPTOR_FROM_DEVICE
, sizeof(struct _URB_CONTROL_DESCRIPTOR_REQUEST
), (PVOID
*)&HidDeviceExtension
->DeviceDescriptor
, &DescriptorLength
, USB_DEVICE_DESCRIPTOR_TYPE
, 0, 0);
1406 if (!NT_SUCCESS(Status
))
1409 // failed to obtain device descriptor
1411 DPRINT1("[HIDUSB] failed to get device descriptor %x\n", Status
);
1416 // now get the configuration descriptor
1418 DescriptorLength
= sizeof(USB_CONFIGURATION_DESCRIPTOR
);
1419 Status
= Hid_GetDescriptor(DeviceObject
, URB_FUNCTION_GET_DESCRIPTOR_FROM_DEVICE
, sizeof(struct _URB_CONTROL_DESCRIPTOR_REQUEST
), (PVOID
*)&HidDeviceExtension
->ConfigurationDescriptor
, &DescriptorLength
, USB_CONFIGURATION_DESCRIPTOR_TYPE
, 0, 0);
1420 if (!NT_SUCCESS(Status
))
1423 // failed to obtain device descriptor
1425 DPRINT1("[HIDUSB] failed to get device descriptor %x\n", Status
);
1432 ASSERT(DescriptorLength
);
1433 ASSERT(HidDeviceExtension
->ConfigurationDescriptor
);
1434 ASSERT(HidDeviceExtension
->ConfigurationDescriptor
->bLength
);
1437 // store full length
1439 DescriptorLength
= HidDeviceExtension
->ConfigurationDescriptor
->wTotalLength
;
1442 // delete partial configuration descriptor
1444 ExFreePool(HidDeviceExtension
->ConfigurationDescriptor
);
1445 HidDeviceExtension
->ConfigurationDescriptor
= NULL
;
1448 // get full configuration descriptor
1450 Status
= Hid_GetDescriptor(DeviceObject
, URB_FUNCTION_GET_DESCRIPTOR_FROM_DEVICE
, sizeof(struct _URB_CONTROL_DESCRIPTOR_REQUEST
), (PVOID
*)&HidDeviceExtension
->ConfigurationDescriptor
, &DescriptorLength
, USB_CONFIGURATION_DESCRIPTOR_TYPE
, 0, 0);
1451 if (!NT_SUCCESS(Status
))
1454 // failed to obtain device descriptor
1456 DPRINT1("[HIDUSB] failed to get device descriptor %x\n", Status
);
1461 // now parse the descriptors
1463 InterfaceDescriptor
= USBD_ParseConfigurationDescriptorEx(HidDeviceExtension
->ConfigurationDescriptor
,
1464 HidDeviceExtension
->ConfigurationDescriptor
,
1467 USB_DEVICE_CLASS_HUMAN_INTERFACE
,
1470 if (!InterfaceDescriptor
)
1473 // no interface class
1475 DPRINT1("[HIDUSB] HID Class found\n");
1476 return STATUS_UNSUCCESSFUL
;
1482 ASSERT(InterfaceDescriptor
->bInterfaceClass
== USB_DEVICE_CLASS_HUMAN_INTERFACE
);
1483 ASSERT(InterfaceDescriptor
->bDescriptorType
== USB_INTERFACE_DESCRIPTOR_TYPE
);
1484 ASSERT(InterfaceDescriptor
->bLength
== sizeof(USB_INTERFACE_DESCRIPTOR
));
1487 // now set the device idle
1489 Hid_SetIdle(DeviceObject
);
1492 // move to next descriptor
1494 HidDescriptor
= (PHID_DESCRIPTOR
)((ULONG_PTR
)InterfaceDescriptor
+ InterfaceDescriptor
->bLength
);
1495 ASSERT(HidDescriptor
->bLength
>= 2);
1498 // check if this is the hid descriptor
1500 if (HidDescriptor
->bLength
== sizeof(HID_DESCRIPTOR
) && HidDescriptor
->bDescriptorType
== HID_HID_DESCRIPTOR_TYPE
)
1505 HidDeviceExtension
->HidDescriptor
= HidDescriptor
;
1508 // select configuration
1510 Status
= Hid_SelectConfiguration(DeviceObject
);
1511 ASSERT(Status
== STATUS_SUCCESS
);
1516 DPRINT("[HIDUSB] SelectConfiguration %x\n", Status
);
1521 Hid_GetProtocol(DeviceObject
);
1526 // FIXME parse hid descriptor
1534 Hid_GetProtocol(DeviceObject
);
1535 return STATUS_SUCCESS
;
1542 IN PDEVICE_OBJECT DeviceObject
,
1546 PIO_STACK_LOCATION IoStack
;
1547 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
1548 PHID_DEVICE_EXTENSION DeviceExtension
;
1552 // get device extension
1554 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
1555 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
1558 // get current stack location
1560 IoStack
= IoGetCurrentIrpStackLocation(Irp
);
1561 DPRINT("[HIDUSB] Pnp %x\n", IoStack
->MinorFunction
);
1564 // handle requests based on request type
1566 switch(IoStack
->MinorFunction
)
1568 case IRP_MN_REMOVE_DEVICE
:
1571 // pass request onto lower driver
1573 IoSkipCurrentIrpStackLocation(Irp
);
1574 Status
= IoCallDriver(DeviceExtension
->NextDeviceObject
, Irp
);
1579 if (HidDeviceExtension
->ConfigurationDescriptor
)
1581 ExFreePool(HidDeviceExtension
->ConfigurationDescriptor
);
1582 HidDeviceExtension
->ConfigurationDescriptor
= NULL
;
1586 // delete and detach device
1588 IoDetachDevice(DeviceExtension
->NextDeviceObject
);
1589 IoDeleteDevice(DeviceObject
);
1593 case IRP_MN_QUERY_PNP_DEVICE_STATE
:
1596 // device can not be disabled
1598 Irp
->IoStatus
.Information
|= PNP_DEVICE_NOT_DISABLEABLE
;
1601 // pass request to next request
1603 IoSkipCurrentIrpStackLocation(Irp
);
1604 Status
= IoCallDriver(DeviceExtension
->NextDeviceObject
, Irp
);
1611 case IRP_MN_QUERY_STOP_DEVICE
:
1612 case IRP_MN_QUERY_REMOVE_DEVICE
:
1615 // we're fine with it
1617 Irp
->IoStatus
.Status
= STATUS_SUCCESS
;
1620 // pass request to next driver
1622 IoSkipCurrentIrpStackLocation(Irp
);
1623 Status
= IoCallDriver(DeviceExtension
->NextDeviceObject
, Irp
);
1630 case IRP_MN_STOP_DEVICE
:
1633 // FIXME: unconfigure the device
1639 KeInitializeEvent(&Event
, NotificationEvent
, FALSE
);
1640 IoCopyCurrentIrpStackLocationToNext(Irp
);
1641 IoSetCompletionRoutine(Irp
, Hid_PnpCompletion
, (PVOID
)&Event
, TRUE
, TRUE
, TRUE
);
1644 // send irp and wait for completion
1646 Status
= IoCallDriver(DeviceExtension
->NextDeviceObject
, Irp
);
1647 if (Status
== STATUS_PENDING
)
1649 KeWaitForSingleObject(&Event
, Executive
, KernelMode
, FALSE
, NULL
);
1650 Status
= Irp
->IoStatus
.Status
;
1656 if (HidDeviceExtension
->HidDescriptor
)
1658 ExFreePool(HidDeviceExtension
->HidDescriptor
);
1659 HidDeviceExtension
->HidDescriptor
= NULL
;
1665 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
1668 case IRP_MN_QUERY_CAPABILITIES
:
1673 KeInitializeEvent(&Event
, NotificationEvent
, FALSE
);
1674 IoCopyCurrentIrpStackLocationToNext(Irp
);
1675 IoSetCompletionRoutine(Irp
, Hid_PnpCompletion
, (PVOID
)&Event
, TRUE
, TRUE
, TRUE
);
1678 // send irp and wait for completion
1680 Status
= IoCallDriver(DeviceExtension
->NextDeviceObject
, Irp
);
1681 if (Status
== STATUS_PENDING
)
1683 KeWaitForSingleObject(&Event
, Executive
, KernelMode
, FALSE
, NULL
);
1684 Status
= Irp
->IoStatus
.Status
;
1688 // don't need to safely remove
1690 IoStack
->Parameters
.DeviceCapabilities
.Capabilities
->SurpriseRemovalOK
= TRUE
;
1695 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
1698 case IRP_MN_START_DEVICE
:
1703 KeInitializeEvent(&Event
, NotificationEvent
, FALSE
);
1704 IoCopyCurrentIrpStackLocationToNext(Irp
);
1705 IoSetCompletionRoutine(Irp
, Hid_PnpCompletion
, (PVOID
)&Event
, TRUE
, TRUE
, TRUE
);
1708 // send irp and wait for completion
1710 Status
= IoCallDriver(DeviceExtension
->NextDeviceObject
, Irp
);
1711 if (Status
== STATUS_PENDING
)
1713 KeWaitForSingleObject(&Event
, Executive
, KernelMode
, FALSE
, NULL
);
1714 Status
= Irp
->IoStatus
.Status
;
1718 // did the device successfully start
1720 if (!NT_SUCCESS(Status
))
1725 DPRINT1("HIDUSB: IRP_MN_START_DEVICE failed with %x\n", Status
);
1726 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
1733 Status
= Hid_PnpStart(DeviceObject
);
1738 Irp
->IoStatus
.Status
= Status
;
1739 DPRINT("[HIDUSB] IRP_MN_START_DEVICE Status %x\n", Status
);
1740 IoCompleteRequest(Irp
, IO_NO_INCREMENT
);
1746 // forward and forget request
1748 IoSkipCurrentIrpStackLocation(Irp
);
1749 return IoCallDriver(DeviceExtension
->NextDeviceObject
, Irp
);
1757 IN PDRIVER_OBJECT DriverObject
,
1758 IN PDEVICE_OBJECT DeviceObject
)
1760 PHID_USB_DEVICE_EXTENSION HidDeviceExtension
;
1761 PHID_DEVICE_EXTENSION DeviceExtension
;
1764 // get device extension
1766 DeviceExtension
= (PHID_DEVICE_EXTENSION
)DeviceObject
->DeviceExtension
;
1767 HidDeviceExtension
= (PHID_USB_DEVICE_EXTENSION
)DeviceExtension
->MiniDeviceExtension
;
1772 KeInitializeEvent(&HidDeviceExtension
->Event
, NotificationEvent
, FALSE
);
1777 return STATUS_SUCCESS
;
1783 IN PDRIVER_OBJECT DriverObject
)
1792 IN PDRIVER_OBJECT DriverObject
,
1793 IN PUNICODE_STRING RegPath
)
1795 HID_MINIDRIVER_REGISTRATION Registration
;
1799 // initialize driver object
1801 DriverObject
->MajorFunction
[IRP_MJ_CREATE
] = HidCreate
;
1802 DriverObject
->MajorFunction
[IRP_MJ_CLOSE
] = HidCreate
;
1803 DriverObject
->MajorFunction
[IRP_MJ_INTERNAL_DEVICE_CONTROL
] = HidInternalDeviceControl
;
1804 DriverObject
->MajorFunction
[IRP_MJ_POWER
] = HidPower
;
1805 DriverObject
->MajorFunction
[IRP_MJ_SYSTEM_CONTROL
] = HidSystemControl
;
1806 DriverObject
->MajorFunction
[IRP_MJ_PNP
] = HidPnp
;
1807 DriverObject
->DriverExtension
->AddDevice
= HidAddDevice
;
1808 DriverObject
->DriverUnload
= Hid_Unload
;
1811 // prepare registration info
1813 RtlZeroMemory(&Registration
, sizeof(HID_MINIDRIVER_REGISTRATION
));
1816 // fill in registration info
1818 Registration
.Revision
= HID_REVISION
;
1819 Registration
.DriverObject
= DriverObject
;
1820 Registration
.RegistryPath
= RegPath
;
1821 Registration
.DeviceExtensionSize
= sizeof(HID_USB_DEVICE_EXTENSION
);
1822 Registration
.DevicesArePolled
= FALSE
;
1827 Status
= HidRegisterMinidriver(&Registration
);
1832 DPRINT("********* HIDUSB *********\n");
1833 DPRINT("HIDUSB Registration Status %x\n", Status
);