[PATCH 5/6] user32: Use HID ioctls directly.

Zebediah Figura wine at gitlab.winehq.org
Wed May 25 14:35:49 CDT 2022


From: Zebediah Figura <zfigura at codeweavers.com>

Signed-off-by: Zebediah Figura <zfigura at codeweavers.com>
---
 dlls/user32/Makefile.in |  2 +-
 dlls/user32/rawinput.c  | 55 ++++++++++++++++++++++++-----------------
 2 files changed, 34 insertions(+), 23 deletions(-)

diff --git a/dlls/user32/Makefile.in b/dlls/user32/Makefile.in
index 4a413746de7..c266d90c045 100644
--- a/dlls/user32/Makefile.in
+++ b/dlls/user32/Makefile.in
@@ -3,7 +3,7 @@ MODULE    = user32.dll
 IMPORTLIB = user32
 IMPORTS   = $(PNG_PE_LIBS) gdi32 version sechost advapi32 kernelbase win32u
 EXTRAINCL = $(PNG_PE_CFLAGS)
-DELAYIMPORTS = hid setupapi imm32
+DELAYIMPORTS = setupapi imm32
 
 C_SRCS = \
 	button.c \
diff --git a/dlls/user32/rawinput.c b/dlls/user32/rawinput.c
index 86f011579bf..5dd3e01751b 100644
--- a/dlls/user32/rawinput.c
+++ b/dlls/user32/rawinput.c
@@ -26,11 +26,11 @@
 #include "windef.h"
 #include "winbase.h"
 #include "wingdi.h"
+#include "winioctl.h"
 #include "winnls.h"
 #include "winreg.h"
 #include "winuser.h"
 #include "setupapi.h"
-#include "ddk/hidsdi.h"
 #include "wine/debug.h"
 #include "wine/server.h"
 #include "wine/hid.h"
@@ -53,7 +53,7 @@ struct device
     HANDLE file;
     HANDLE handle;
     RID_DEVICE_INFO info;
-    PHIDP_PREPARSED_DATA data;
+    struct hid_preparsed_data *data;
 };
 
 static struct device *rawinput_devices;
@@ -98,7 +98,7 @@ static BOOL array_reserve(void **elements, unsigned int *capacity, unsigned int
 static struct device *add_device( HDEVINFO set, SP_DEVICE_INTERFACE_DATA *iface, DWORD type )
 {
     SP_DEVINFO_DATA device_data = {sizeof(device_data)};
-    PHIDP_PREPARSED_DATA preparsed_data = NULL;
+    struct hid_preparsed_data *preparsed_data = NULL;
     SP_DEVICE_INTERFACE_DETAIL_DATA_W *detail;
     struct device *device = NULL;
     RID_DEVICE_INFO info;
@@ -149,29 +149,40 @@ static struct device *add_device( HDEVINFO set, SP_DEVICE_INTERFACE_DATA *iface,
     {
         case RIM_TYPEHID:
         {
-            const struct hid_preparsed_data *preparsed;
-            HIDD_ATTRIBUTES attr;
-
-            attr.Size = sizeof(HIDD_ATTRIBUTES);
-            if (!HidD_GetAttributes( device->file, &attr ))
+            HID_COLLECTION_INFORMATION hid_info;
+            IO_STATUS_BLOCK io;
+            NTSTATUS status;
+
+            status = NtDeviceIoControlFile( device->file, NULL, NULL, NULL, &io,
+                                            IOCTL_HID_GET_COLLECTION_INFORMATION,
+                                            NULL, 0, &hid_info, sizeof(hid_info) );
+            if (status)
             {
-                ERR( "Failed to get attributes.\n" );
+                ERR( "Failed to get collection information, status %#x.\n", status );
                 goto fail;
             }
 
-            info.hid.dwVendorId = attr.VendorID;
-            info.hid.dwProductId = attr.ProductID;
-            info.hid.dwVersionNumber = attr.VersionNumber;
+            info.hid.dwVendorId = hid_info.VendorID;
+            info.hid.dwProductId = hid_info.ProductID;
+            info.hid.dwVersionNumber = hid_info.VersionNumber;
+
+            if (!(preparsed_data = malloc( hid_info.DescriptorSize )))
+            {
+                ERR( "Failed to allocate memory.\n" );
+                goto fail;
+            }
 
-            if (!HidD_GetPreparsedData( file, &preparsed_data ))
+            status = NtDeviceIoControlFile( device->file, NULL, NULL, NULL, &io,
+                                            IOCTL_HID_GET_COLLECTION_DESCRIPTOR,
+                                            NULL, 0, preparsed_data, hid_info.DescriptorSize );
+            if (status)
             {
-                ERR( "Failed to get preparsed data.\n" );
+                ERR( "Failed to get collection descriptor, status %#x.\n", status );
                 goto fail;
             }
-            preparsed = (struct hid_preparsed_data *)preparsed_data;
 
-            info.hid.usUsagePage = preparsed->usage_page;
-            info.hid.usUsage = preparsed->usage;
+            info.hid.usUsagePage = preparsed_data->usage_page;
+            info.hid.usUsage = preparsed_data->usage;
             break;
         }
 
@@ -199,7 +210,7 @@ static struct device *add_device( HDEVINFO set, SP_DEVICE_INTERFACE_DATA *iface,
     if (device)
     {
         TRACE("Updating device %x / %s.\n", handle, debugstr_w(detail->DevicePath));
-        HidD_FreePreparsedData(device->data);
+        free(device->data);
         CloseHandle(device->file);
         free(device->detail);
     }
@@ -244,7 +255,7 @@ void rawinput_update_device_list(void)
     /* destroy previous list */
     for (idx = 0; idx < rawinput_devices_count; ++idx)
     {
-        HidD_FreePreparsedData(rawinput_devices[idx].data);
+        free(rawinput_devices[idx].data);
         CloseHandle(rawinput_devices[idx].file);
         free(rawinput_devices[idx].detail);
     }
@@ -788,12 +799,12 @@ UINT WINAPI GetRawInputDeviceInfoW(HANDLE handle, UINT command, void *data, UINT
         break;
 
     case RIDI_PREPARSEDDATA:
-        if (!(preparsed = (struct hid_preparsed_data *)device->data)) len = 0;
+        if (!(preparsed = device->data)) len = 0;
         else len = preparsed->caps_size + FIELD_OFFSET(struct hid_preparsed_data, value_caps[0]) +
                    preparsed->number_link_collection_nodes * sizeof(struct hid_collection_node);
 
-        if (device->data && len <= data_len && data)
-            memcpy(data, device->data, len);
+        if (preparsed && len <= data_len && data)
+            memcpy(data, preparsed, len);
         *data_size = len;
         break;
 
-- 
GitLab


https://gitlab.winehq.org/wine/wine/-/merge_requests/130



More information about the wine-devel mailing list