Signed-off-by: Zhiyi Zhang <zzhang(a)codeweavers.com>
---
dlls/d3d12/tests/d3d12.c | 2 +-
dlls/dxgi/tests/dxgi.c | 4 ++--
dlls/wined3d/adapter_gl.c | 6 +++++-
dlls/wined3d/adapter_vk.c | 18 ++++++++++-------
dlls/wined3d/directx.c | 31 ++++++++++++++++++++----------
dlls/wined3d/utils.c | 35 ++++++++++++++++++++++++++++++++++
dlls/wined3d/wined3d_private.h | 3 ++-
7 files changed, 77 insertions(+), 22 deletions(-)
diff --git a/dlls/d3d12/tests/d3d12.c b/dlls/d3d12/tests/d3d12.c
index 0200047fd17..8c57f07357c 100644
--- a/dlls/d3d12/tests/d3d12.c
+++ b/dlls/d3d12/tests/d3d12.c
@@ -139,7 +139,7 @@ static void print_adapter_info(void)
hr = CreateDXGIFactory2(0, &IID_IDXGIFactory4, (void **)&factory);
ok(hr == S_OK, "Failed to create factory, hr %#x.\n", hr);
hr = IDXGIFactory4_EnumAdapterByLuid(factory, luid, &IID_IDXGIAdapter, (void **)&adapter);
- todo_wine ok(hr == S_OK, "Failed to enum adapter by LUID, hr %#x.\n", hr);
+ ok(hr == S_OK, "Failed to enum adapter by LUID, hr %#x.\n", hr);
IDXGIFactory4_Release(factory);
if (FAILED(hr))
diff --git a/dlls/dxgi/tests/dxgi.c b/dlls/dxgi/tests/dxgi.c
index ea896260c76..59b23918de3 100644
--- a/dlls/dxgi/tests/dxgi.c
+++ b/dlls/dxgi/tests/dxgi.c
@@ -973,7 +973,7 @@ static void test_adapter_luid(void)
ok(hr == DXGI_ERROR_NOT_FOUND, "Got unexpected hr %#x.\n", hr);
/* Older versions of WARP aren't enumerated by IDXGIFactory_EnumAdapters(). */
- todo_wine ok(found_adapter_count == 1 || broken(is_null_luid_adapter),
+ ok(found_adapter_count == 1 || broken(is_null_luid_adapter),
"Found %u adapters for LUID %08x:%08x.\n",
found_adapter_count, device_adapter_desc.AdapterLuid.HighPart,
device_adapter_desc.AdapterLuid.LowPart);
@@ -996,7 +996,7 @@ static void test_adapter_luid(void)
hr = IDXGIFactory4_EnumAdapterByLuid(factory4, device_adapter_desc.AdapterLuid,
&IID_IDXGIAdapter, (void **)&adapter);
- todo_wine ok(hr == S_OK, "Failed to enum adapter by LUID, hr %#x.\n", hr);
+ ok(hr == S_OK, "Failed to enum adapter by LUID, hr %#x.\n", hr);
if (SUCCEEDED(hr))
{
hr = IDXGIAdapter_GetDesc(adapter, &desc);
diff --git a/dlls/wined3d/adapter_gl.c b/dlls/wined3d/adapter_gl.c
index a97e7bd7a41..bc59d1b7439 100644
--- a/dlls/wined3d/adapter_gl.c
+++ b/dlls/wined3d/adapter_gl.c
@@ -5136,12 +5136,16 @@ static BOOL wined3d_adapter_gl_init(struct wined3d_adapter_gl *adapter_gl,
};
struct wined3d_gl_info *gl_info = &adapter_gl->a.gl_info;
struct wined3d_caps_gl_ctx caps_gl_ctx = {0};
+ LUID primary_luid, *luid = NULL;
unsigned int i;
TRACE("adapter_gl %p, ordinal %u, wined3d_creation_flags %#x.\n",
adapter_gl, ordinal, wined3d_creation_flags);
- if (!wined3d_adapter_init(&adapter_gl->a, ordinal, &wined3d_adapter_gl_ops))
+ if (ordinal == 0 && wined3d_get_primary_adapter_luid(&primary_luid))
+ luid = &primary_luid;
+
+ if (!wined3d_adapter_init(&adapter_gl->a, ordinal, luid, &wined3d_adapter_gl_ops))
return FALSE;
/* Dynamically load all GL core functions */
diff --git a/dlls/wined3d/adapter_vk.c b/dlls/wined3d/adapter_vk.c
index 1e4d663dcb4..57972dbb7e7 100644
--- a/dlls/wined3d/adapter_vk.c
+++ b/dlls/wined3d/adapter_vk.c
@@ -2166,17 +2166,15 @@ static BOOL wined3d_adapter_vk_init(struct wined3d_adapter_vk *adapter_vk,
struct wined3d_adapter *adapter = &adapter_vk->a;
VkPhysicalDeviceIDProperties id_properties;
VkPhysicalDeviceProperties2 properties2;
+ LUID *luid = NULL;
TRACE("adapter_vk %p, ordinal %u, wined3d_creation_flags %#x.\n",
adapter_vk, ordinal, wined3d_creation_flags);
- if (!wined3d_adapter_init(adapter, ordinal, &wined3d_adapter_vk_ops))
- return FALSE;
-
if (!wined3d_init_vulkan(vk_info))
{
WARN("Failed to initialize Vulkan.\n");
- goto fail;
+ return FALSE;
}
if (!(adapter_vk->physical_device = get_vulkan_physical_device(vk_info)))
@@ -2195,6 +2193,12 @@ static BOOL wined3d_adapter_vk_init(struct wined3d_adapter_vk *adapter_vk,
VK_CALL(vkGetPhysicalDeviceMemoryProperties(adapter_vk->physical_device, &adapter_vk->memory_properties));
+ if (id_properties.deviceLUIDValid)
+ luid = (LUID *)id_properties.deviceLUID;
+
+ if (!wined3d_adapter_init(adapter, ordinal, luid, &wined3d_adapter_vk_ops))
+ goto fail_vulkan;
+
adapter_vk_init_driver_info(adapter_vk, &properties2.properties);
adapter->vram_bytes_used = 0;
TRACE("Emulating 0x%s bytes of video ram.\n", wine_dbgstr_longlong(adapter->driver_info.vram_bytes));
@@ -2203,7 +2207,7 @@ static BOOL wined3d_adapter_vk_init(struct wined3d_adapter_vk *adapter_vk,
memcpy(&adapter->device_uuid, id_properties.deviceUUID, sizeof(adapter->device_uuid));
if (!wined3d_adapter_vk_init_format_info(adapter_vk, vk_info))
- goto fail_vulkan;
+ goto fail;
adapter->vertex_pipe = wined3d_spirv_vertex_pipe_init_vk();
adapter->fragment_pipe = wined3d_spirv_fragment_pipe_init_vk();
@@ -2214,11 +2218,11 @@ static BOOL wined3d_adapter_vk_init(struct wined3d_adapter_vk *adapter_vk,
return TRUE;
+fail:
+ wined3d_adapter_cleanup(adapter);
fail_vulkan:
VK_CALL(vkDestroyInstance(vk_info->instance, NULL));
wined3d_unload_vulkan(vk_info);
-fail:
- wined3d_adapter_cleanup(adapter);
return FALSE;
}
diff --git a/dlls/wined3d/directx.c b/dlls/wined3d/directx.c
index b5de589d33c..454125c1462 100644
--- a/dlls/wined3d/directx.c
+++ b/dlls/wined3d/directx.c
@@ -2903,6 +2903,7 @@ static void wined3d_adapter_no3d_init_d3d_info(struct wined3d_adapter *adapter,
static struct wined3d_adapter *wined3d_adapter_no3d_create(unsigned int ordinal, unsigned int wined3d_creation_flags)
{
struct wined3d_adapter *adapter;
+ LUID primary_luid, *luid = NULL;
static const struct wined3d_gpu_description gpu_description =
{
@@ -2914,7 +2915,10 @@ static struct wined3d_adapter *wined3d_adapter_no3d_create(unsigned int ordinal,
if (!(adapter = heap_alloc_zero(sizeof(*adapter))))
return NULL;
- if (!wined3d_adapter_init(adapter, ordinal, &wined3d_adapter_no3d_ops))
+ if (ordinal == 0 && wined3d_get_primary_adapter_luid(&primary_luid))
+ luid = &primary_luid;
+
+ if (!wined3d_adapter_init(adapter, ordinal, luid, &wined3d_adapter_no3d_ops))
{
heap_free(adapter);
return NULL;
@@ -2942,7 +2946,7 @@ static struct wined3d_adapter *wined3d_adapter_no3d_create(unsigned int ordinal,
return adapter;
}
-BOOL wined3d_adapter_init(struct wined3d_adapter *adapter, unsigned int ordinal,
+BOOL wined3d_adapter_init(struct wined3d_adapter *adapter, unsigned int ordinal, const LUID *luid,
const struct wined3d_adapter_ops *adapter_ops)
{
DISPLAY_DEVICEW display_device;
@@ -2953,6 +2957,21 @@ BOOL wined3d_adapter_init(struct wined3d_adapter *adapter, unsigned int ordinal,
adapter->ordinal = ordinal;
adapter->output_count = 0;
+ if (luid)
+ {
+ adapter->luid = *luid;
+ }
+ else
+ {
+ WARN("Allocating a random LUID.\n");
+ if (!AllocateLocallyUniqueId(&adapter->luid))
+ {
+ ERR("Failed to allocate a LUID, error %#x.\n", GetLastError());
+ return FALSE;
+ }
+ }
+ TRACE("adapter %p LUID %08x:%08x.\n", adapter, adapter->luid.HighPart, adapter->luid.LowPart);
+
display_device.cb = sizeof(display_device);
EnumDisplayDevicesW(NULL, ordinal, &display_device, 0);
TRACE("Display device: %s.\n", debugstr_w(display_device.DeviceName));
@@ -2972,14 +2991,6 @@ BOOL wined3d_adapter_init(struct wined3d_adapter *adapter, unsigned int ordinal,
}
adapter->output_count = 1;
- if (!AllocateLocallyUniqueId(&adapter->luid))
- {
- ERR("Failed to set adapter LUID (%#x).\n", GetLastError());
- goto done;
- }
- TRACE("Allocated LUID %08x:%08x for adapter %p.\n",
- adapter->luid.HighPart, adapter->luid.LowPart, adapter);
-
memset(&adapter->driver_uuid, 0, sizeof(adapter->driver_uuid));
memset(&adapter->device_uuid, 0, sizeof(adapter->device_uuid));
diff --git a/dlls/wined3d/utils.c b/dlls/wined3d/utils.c
index da17ee7296b..eaa391fafbe 100644
--- a/dlls/wined3d/utils.c
+++ b/dlls/wined3d/utils.c
@@ -5719,6 +5719,41 @@ void get_fog_start_end(const struct wined3d_context *context, const struct wined
}
}
+static BOOL wined3d_get_primary_display(WCHAR *display)
+{
+ DISPLAY_DEVICEW display_device;
+ DWORD device_idx = 0;
+
+ display_device.cb = sizeof(display_device);
+ while (EnumDisplayDevicesW(NULL, device_idx++, &display_device, 0))
+ {
+ if (display_device.StateFlags & DISPLAY_DEVICE_PRIMARY_DEVICE)
+ {
+ lstrcpyW(display, display_device.DeviceName);
+ return TRUE;
+ }
+ }
+
+ return FALSE;
+}
+
+BOOL wined3d_get_primary_adapter_luid(LUID *luid)
+{
+ D3DKMT_OPENADAPTERFROMGDIDISPLAYNAME open_adapter_param;
+ D3DKMT_CLOSEADAPTER close_adapter_param;
+
+ if (!wined3d_get_primary_display(open_adapter_param.DeviceName))
+ return FALSE;
+
+ if (D3DKMTOpenAdapterFromGdiDisplayName(&open_adapter_param))
+ return FALSE;
+
+ *luid = open_adapter_param.AdapterLuid;
+ close_adapter_param.hAdapter = open_adapter_param.hAdapter;
+ D3DKMTCloseAdapter(&close_adapter_param);
+ return TRUE;
+}
+
/* Note: It's the caller's responsibility to ensure values can be expressed
* in the requested format. UNORM formats for example can only express values
* in the range 0.0f -> 1.0f. */
diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h
index ceb6794db0b..342aee64f31 100644
--- a/dlls/wined3d/wined3d_private.h
+++ b/dlls/wined3d/wined3d_private.h
@@ -3300,9 +3300,10 @@ struct wined3d_adapter
const struct wined3d_adapter_ops *adapter_ops;
};
-BOOL wined3d_adapter_init(struct wined3d_adapter *adapter, unsigned int ordinal,
+BOOL wined3d_adapter_init(struct wined3d_adapter *adapter, unsigned int ordinal, const LUID *luid,
const struct wined3d_adapter_ops *adapter_ops) DECLSPEC_HIDDEN;
void wined3d_adapter_cleanup(struct wined3d_adapter *adapter) DECLSPEC_HIDDEN;
+BOOL wined3d_get_primary_adapter_luid(LUID *luid) DECLSPEC_HIDDEN;
struct wined3d_adapter_gl
{
--
2.25.1