Signed-off-by: Rémi Bernon rbernon@codeweavers.com --- dlls/hidclass.sys/device.c | 69 ++++------------------------ dlls/ntoskrnl.exe/tests/driver_hid.c | 8 ---- dlls/ntoskrnl.exe/tests/ntoskrnl.c | 5 +- 3 files changed, 9 insertions(+), 73 deletions(-)
diff --git a/dlls/hidclass.sys/device.c b/dlls/hidclass.sys/device.c index 44965e118a2..8c0883bbec4 100644 --- a/dlls/hidclass.sys/device.c +++ b/dlls/hidclass.sys/device.c @@ -320,6 +320,10 @@ static void hid_device_xfer_report( BASE_DEVICE_EXTENSION *ext, ULONG code, IRP buffer_len = stack->Parameters.DeviceIoControl.InputBufferLength; buffer = irp->AssociatedIrp.SystemBuffer; break; + case IOCTL_HID_WRITE_REPORT: + buffer_len = stack->Parameters.Write.Length; + buffer = irp->AssociatedIrp.SystemBuffer; + break; }
switch (code) @@ -330,6 +334,7 @@ static void hid_device_xfer_report( BASE_DEVICE_EXTENSION *ext, ULONG code, IRP caps_end = caps + preparsed->value_caps_count[HidP_Input]; break; case IOCTL_HID_SET_OUTPUT_REPORT: + case IOCTL_HID_WRITE_REPORT: report_len = preparsed->caps.OutputReportByteLength; caps = HID_OUTPUT_VALUE_CAPS( preparsed ); caps_end = caps + preparsed->value_caps_count[HidP_Output]; @@ -379,7 +384,9 @@ static void hid_device_xfer_report( BASE_DEVICE_EXTENSION *ext, ULONG code, IRP break; case IOCTL_HID_SET_FEATURE: case IOCTL_HID_SET_OUTPUT_REPORT: + case IOCTL_HID_WRITE_REPORT: call_minidriver( code, ext->u.pdo.parent_fdo, NULL, sizeof(packet), &packet, 0, &irp->IoStatus ); + if (code == IOCTL_HID_WRITE_REPORT && packet.reportId) irp->IoStatus.Information--; break; } } @@ -611,70 +618,10 @@ NTSTATUS WINAPI pdo_read(DEVICE_OBJECT *device, IRP *irp)
NTSTATUS WINAPI pdo_write(DEVICE_OBJECT *device, IRP *irp) { - IO_STACK_LOCATION *irpsp = IoGetCurrentIrpStackLocation( irp ); BASE_DEVICE_EXTENSION *ext = device->DeviceExtension; - const WINE_HIDP_PREPARSED_DATA *data = ext->u.pdo.preparsed_data; - HID_XFER_PACKET packet; NTSTATUS status; - ULONG max_len; - BOOL removed; - KIRQL irql; - - KeAcquireSpinLock(&ext->u.pdo.lock, &irql); - removed = ext->u.pdo.removed; - KeReleaseSpinLock(&ext->u.pdo.lock, irql); - - if (removed) - { - irp->IoStatus.Status = STATUS_DELETE_PENDING; - IoCompleteRequest(irp, IO_NO_INCREMENT); - return STATUS_DELETE_PENDING; - } - - if (!irpsp->Parameters.Write.Length) - { - irp->IoStatus.Status = STATUS_INVALID_USER_BUFFER; - IoCompleteRequest( irp, IO_NO_INCREMENT ); - return STATUS_INVALID_USER_BUFFER; - } - - if (irpsp->Parameters.Write.Length < data->caps.OutputReportByteLength) - { - irp->IoStatus.Status = STATUS_INVALID_PARAMETER; - IoCompleteRequest( irp, IO_NO_INCREMENT ); - return STATUS_INVALID_PARAMETER; - } - - irp->IoStatus.Information = 0; - - TRACE_(hid_report)("Device %p Buffer length %i Buffer %p\n", device, irpsp->Parameters.Write.Length, irp->AssociatedIrp.SystemBuffer); - packet.reportId = ((BYTE*)irp->AssociatedIrp.SystemBuffer)[0]; - if (packet.reportId == 0) - { - packet.reportBuffer = &((BYTE*)irp->AssociatedIrp.SystemBuffer)[1]; - packet.reportBufferLen = irpsp->Parameters.Write.Length - 1; - max_len = data->caps.OutputReportByteLength; - } - else - { - packet.reportBuffer = irp->AssociatedIrp.SystemBuffer; - packet.reportBufferLen = irpsp->Parameters.Write.Length; - max_len = (data->reports[data->reportIdx[HidP_Output][packet.reportId]].bitSize + 7) / 8; - } - if (packet.reportBufferLen > max_len) - packet.reportBufferLen = max_len; - - TRACE_(hid_report)("(id %i, len %i buffer %p)\n", packet.reportId, packet.reportBufferLen, packet.reportBuffer); - - call_minidriver( IOCTL_HID_WRITE_REPORT, ext->u.pdo.parent_fdo, NULL, 0, &packet, - sizeof(packet), &irp->IoStatus ); - - if (irp->IoStatus.Status == STATUS_SUCCESS) - irp->IoStatus.Information = irpsp->Parameters.Write.Length; - else - irp->IoStatus.Information = 0;
- TRACE_(hid_report)( "Result 0x%x wrote %li bytes\n", irp->IoStatus.Status, irp->IoStatus.Information ); + hid_device_xfer_report( ext, IOCTL_HID_WRITE_REPORT, irp );
status = irp->IoStatus.Status; IoCompleteRequest( irp, IO_NO_INCREMENT ); diff --git a/dlls/ntoskrnl.exe/tests/driver_hid.c b/dlls/ntoskrnl.exe/tests/driver_hid.c index 83f546aa972..8111af23c06 100644 --- a/dlls/ntoskrnl.exe/tests/driver_hid.c +++ b/dlls/ntoskrnl.exe/tests/driver_hid.c @@ -503,22 +503,14 @@ static NTSTATUS WINAPI driver_internal_ioctl(DEVICE_OBJECT *device, IRP *irp) HID_XFER_PACKET *packet = irp->UserBuffer; ULONG expected_size = 2;
- todo_wine ok(in_size == sizeof(*packet), "got input size %u\n", in_size); - todo_wine ok(!out_size, "got output size %u\n", out_size); ok(packet->reportBufferLen >= expected_size, "got report size %u\n", packet->reportBufferLen);
if (report_id) - { - todo_wine_if(packet->reportBuffer[0] == 0xa5) ok(packet->reportBuffer[0] == report_id, "got report id %x\n", packet->reportBuffer[0]); - } else - { - todo_wine ok(packet->reportBuffer[0] == 0xcd, "got first byte %x\n", packet->reportBuffer[0]); - }
irp->IoStatus.Information = 3; ret = STATUS_SUCCESS; diff --git a/dlls/ntoskrnl.exe/tests/ntoskrnl.c b/dlls/ntoskrnl.exe/tests/ntoskrnl.c index 4909ab202a6..d49f6fe3c7e 100644 --- a/dlls/ntoskrnl.exe/tests/ntoskrnl.c +++ b/dlls/ntoskrnl.exe/tests/ntoskrnl.c @@ -2630,11 +2630,8 @@ static void test_hidp(HANDLE file, HANDLE async_file, int report_id, BOOL polled ret = WriteFile(file, report, caps.OutputReportByteLength * 2, &value, NULL); if (report_id || broken(!ret) /* w7u */) { - todo_wine ok(!ret, "WriteFile succeeded\n"); - todo_wine ok(GetLastError() == ERROR_INVALID_PARAMETER, "WriteFile returned error %u\n", GetLastError()); - todo_wine ok(value == 0, "WriteFile wrote %u\n", value); SetLastError(0xdeadbeef); report[0] = report_id; @@ -2649,7 +2646,7 @@ static void test_hidp(HANDLE file, HANDLE async_file, int report_id, BOOL polled else { ok(ret, "WriteFile failed, last error %u\n", GetLastError()); - todo_wine ok(value == 3, "WriteFile wrote %u\n", value); + ok(value == 3, "WriteFile wrote %u\n", value); }