[PATCH 4/7] winemac.drv: Initialize adapter registry data.

Zhiyi Zhang zzhang at codeweavers.com
Mon Apr 22 07:13:39 CDT 2019


Signed-off-by: Zhiyi Zhang <zzhang at codeweavers.com>
---
 dlls/winemac.drv/display.c | 104 ++++++++++++++++++++++++++++++++++++++++++++-
 1 file changed, 102 insertions(+), 2 deletions(-)

diff --git a/dlls/winemac.drv/display.c b/dlls/winemac.drv/display.c
index b756510875..842a979fd2 100644
--- a/dlls/winemac.drv/display.c
+++ b/dlls/winemac.drv/display.c
@@ -57,6 +57,9 @@ static const WCHAR pixelencodingW[] = {'P','i','x','e','l','E','n','c','o','d','
 static const WCHAR driver_descW[] = {'D','r','i','v','e','r','D','e','s','c',0};
 static const WCHAR graphics_driverW[] = {'G','r','a','p','h','i','c','s','D','r','i','v','e','r',0};
 static const WCHAR video_idW[] = {'V','i','d','e','o','I','D',0};
+static const WCHAR symbolic_link_valueW[]= {'S','y','m','b','o','l','i','c','L','i','n','k','V','a','l','u','e',0};
+static const WCHAR gpu_idW[] = {'G','P','U','I','D',0};
+static const WCHAR state_flagsW[] = {'S','t','a','t','e','F','l','a','g','s',0};
 static const WCHAR guid_fmtW[] = {
     '{','%','0','8','x','-','%','0','4','x','-','%','0','4','x','-','%','0','2','x','%','0','2','x','-',
     '%','0','2','x','%','0','2','x','%','0','2','x','%','0','2','x','%','0','2','x','%','0','2','x','}',0};
@@ -89,6 +92,19 @@ static const WCHAR video_keyW[] = {
     'H','A','R','D','W','A','R','E','\\',
     'D','E','V','I','C','E','M','A','P','\\',
     'V','I','D','E','O',0};
+static const WCHAR adapter_key_fmtW[] = {
+    'S','y','s','t','e','m','\\',
+    'C','u','r','r','e','n','t','C','o','n','t','r','o','l','S','e','t','\\',
+    'C','o','n','t','r','o','l','\\',
+    'V','i','d','e','o','\\',
+    '%','s','\\',
+    '%','0','4','x',0};
+static const WCHAR device_video_fmtW[] = {
+    '\\','D','e','v','i','c','e','\\',
+    'V','i','d','e','o','%','d',0};
+static const WCHAR machine_prefixW[] = {
+    '\\','R','e','g','i','s','t','r','y','\\',
+    'M','a','c','h','i','n','e','\\',0};
 
 
 static CFArrayRef modes;
@@ -1529,6 +1545,70 @@ fail:
     return ret;
 }
 
+/***********************************************************************
+ *              macdrv_init_adapter
+ *
+ * Initialize an adapter.
+ *
+ * Return FALSE on failure and TRUE on success.
+ */
+static BOOL macdrv_init_adapter(HKEY video_hkey, int video_index, int gpu_index, int adapter_index,
+                                const WCHAR *guid_string, const WCHAR *gpu_driver, const struct macdrv_gpu *gpu,
+                                const struct macdrv_adapter *adapter)
+{
+    WCHAR adapter_keyW[MAX_PATH];
+    WCHAR key_nameW[MAX_PATH];
+    WCHAR bufferW[1024];
+    HKEY hkey = NULL;
+    BOOL ret = FALSE;
+    LSTATUS ls;
+
+    sprintfW(key_nameW, device_video_fmtW, video_index);
+    strcpyW(bufferW, machine_prefixW);
+    sprintfW(adapter_keyW, adapter_key_fmtW, guid_string, adapter_index);
+    strcatW(bufferW, adapter_keyW);
+
+    /* Write value of \Device\Video? (adapter key) in HKLM\HARDWARE\DEVICEMAP\VIDEO\ */
+    if (RegSetValueExW(video_hkey, key_nameW, 0, REG_SZ, (const BYTE *)bufferW, (strlenW(bufferW) + 1) * sizeof(WCHAR)))
+        goto fail;
+
+    /* Create HKLM\System\CurrentControlSet\Control\Video\{GPU GUID}\{Adapter Index} link to GPU driver */
+    ls = RegCreateKeyExW(HKEY_LOCAL_MACHINE, adapter_keyW, 0, NULL, REG_OPTION_VOLATILE | REG_OPTION_CREATE_LINK,
+                         KEY_ALL_ACCESS, NULL, &hkey, NULL);
+    if (ls == ERROR_ALREADY_EXISTS)
+        RegCreateKeyExW(HKEY_LOCAL_MACHINE, adapter_keyW, 0, NULL, REG_OPTION_VOLATILE | REG_OPTION_OPEN_LINK,
+                        KEY_ALL_ACCESS, NULL, &hkey, NULL);
+    if (RegSetValueExW(hkey, symbolic_link_valueW, 0, REG_LINK, (const BYTE *)gpu_driver,
+                       strlenW(gpu_driver) * sizeof(WCHAR)))
+        goto fail;
+    RegCloseKey(hkey);
+    hkey = NULL;
+
+    /* FIXME:
+     * Following information are Wine specific, they don't really exist on Windows. They are used so that we can
+     * implement EnumDisplayDevices etc by querying registry only. These information are most likely reported by the
+     * device driver on Windows */
+    RegCreateKeyExW(HKEY_CURRENT_CONFIG, adapter_keyW, 0, NULL, REG_OPTION_VOLATILE, KEY_WRITE, NULL, &hkey, NULL);
+
+    /* Write GPU instance path so that we can find the GPU instance via adapters quickly. Another way is trying to match
+     * them via the GUID in Device Paramters/VideoID, but it would required enumrating all GPU instances */
+    sprintfW(bufferW, gpu_instance_fmtW, gpu->vendor_id, gpu->device_id, gpu->subsys_id, gpu->revision_id, gpu_index);
+    if (RegSetValueExW(hkey, gpu_idW, 0, REG_SZ, (const BYTE *)bufferW, (strlenW(bufferW) + 1) * sizeof(WCHAR)))
+        goto fail;
+
+    /* Write StateFlags */
+    if (RegSetValueExW(hkey, state_flagsW, 0, REG_DWORD, (const BYTE *)&adapter->state_flags,
+                       sizeof(adapter->state_flags)))
+        goto fail;
+
+    ret = TRUE;
+fail:
+    RegCloseKey(hkey);
+    if (!ret)
+        ERR("Failed to initialize adapter\n");
+    return ret;
+}
+
 static void prepare_devices(void)
 {
     static const BOOL not_present = FALSE;
@@ -1578,10 +1658,12 @@ static void cleanup_devices(void)
 BOOL macdrv_init_display_devices(void)
 {
     struct macdrv_gpu *gpus = NULL;
-    INT gpu_count;
-    INT gpu;
+    struct macdrv_adapter *adapters = NULL;
+    INT gpu_count, adapter_count;
+    INT gpu, adapter;
     HDEVINFO gpu_devinfo = NULL;
     HKEY video_hkey = NULL;
+    INT video_index = 0;
     DWORD disposition = 0;
     WCHAR guidW[40];
     WCHAR driverW[1024];
@@ -1617,6 +1699,22 @@ BOOL macdrv_init_display_devices(void)
     {
         if (!macdrv_init_gpu(gpu_devinfo, &gpus[gpu], gpu, guidW, driverW))
             goto fail;
+
+        /* Initialize adapters */
+        if (macdrv_get_adapters(gpus[gpu].id, &adapters, &adapter_count))
+            goto fail;
+
+        for (adapter = 0; adapter < adapter_count; adapter++)
+        {
+            if (!macdrv_init_adapter(video_hkey, video_index, gpu, adapter, guidW, driverW, &gpus[gpu],
+                                      &adapters[adapter]))
+                goto fail;
+
+            video_index++;
+        }
+
+        macdrv_free_adapters(adapters);
+        adapters = NULL;
     }
 
     ret = TRUE;
@@ -1626,6 +1724,8 @@ fail:
     RegCloseKey(video_hkey);
     if (gpus)
         macdrv_free_gpus(gpus);
+    if (adapters)
+        macdrv_free_adapters(adapters);
     if (!ret)
         ERR("Failed to initialize display devices\n");
     return ret;
-- 
2.15.2 (Apple Git-101.1)





More information about the wine-devel mailing list