From: Giovanni Mascellani gmascellani@codeweavers.com
--- dlls/dxgi/swapchain.c | 16 +++++++++++++++- dlls/dxgi/tests/dxgi.c | 18 ++++++++++++++++-- 2 files changed, 31 insertions(+), 3 deletions(-)
diff --git a/dlls/dxgi/swapchain.c b/dlls/dxgi/swapchain.c index 554e910de11..910286b8c5f 100644 --- a/dlls/dxgi/swapchain.c +++ b/dlls/dxgi/swapchain.c @@ -2564,10 +2564,24 @@ static HRESULT STDMETHODCALLTYPE d3d12_swapchain_GetMaximumFrameLatency(IDXGISwa static HANDLE STDMETHODCALLTYPE d3d12_swapchain_GetFrameLatencyWaitableObject(IDXGISwapChain4 *iface) { struct d3d12_swapchain *swapchain = d3d12_swapchain_from_IDXGISwapChain4(iface); + HANDLE dup; + BOOL ret;
TRACE("iface %p.\n", iface);
- return swapchain->frame_latency_event; + if (!swapchain->frame_latency_event) + return NULL; + + ret = DuplicateHandle(GetCurrentProcess(), swapchain->frame_latency_event, GetCurrentProcess(), + &dup, 0, FALSE, DUPLICATE_SAME_ACCESS); + + if (!ret) + { + ERR("Cannot duplicate handle, last error %lu.\n", GetLastError()); + return NULL; + } + + return dup; }
static HRESULT STDMETHODCALLTYPE d3d12_swapchain_SetMatrixTransform(IDXGISwapChain4 *iface, diff --git a/dlls/dxgi/tests/dxgi.c b/dlls/dxgi/tests/dxgi.c index 0661c68b109..4cd122995ef 100644 --- a/dlls/dxgi/tests/dxgi.c +++ b/dlls/dxgi/tests/dxgi.c @@ -6981,13 +6981,14 @@ static void test_frame_latency_event(IUnknown *device, BOOL is_d3d12) IDXGISwapChain1 *swapchain1; IDXGIFactory2 *factory2; IDXGIFactory *factory; + HANDLE event, event2; UINT frame_latency; DWORD wait_result; ULONG ref_count; unsigned int i; - HANDLE event; HWND window; HRESULT hr; + BOOL ret;
get_factory(device, is_d3d12, &factory);
@@ -7052,7 +7053,20 @@ static void test_frame_latency_event(IUnknown *device, BOOL is_d3d12) IDXGISwapChain1_Release(swapchain1);
event = IDXGISwapChain2_GetFrameLatencyWaitableObject(swapchain2); - ok(!!event, "Got unexpected event %p.\n", event); + ok(!!event, "Got unexpected NULL event.\n"); + + /* a new duplicate handle is returned each time */ + event2 = IDXGISwapChain2_GetFrameLatencyWaitableObject(swapchain2); + ok(!!event2, "Got unexpected NULL event.\n"); + ok(event != event2, "Got the same event twice %p.\n", event); + + ret = CloseHandle(event); + ok(!!ret, "Failed to close handle, last error %lu.\n", GetLastError()); + ret = CloseHandle(event2); + ok(!!ret, "Failed to close handle, last error %lu.\n", GetLastError()); + + event = IDXGISwapChain2_GetFrameLatencyWaitableObject(swapchain2); + ok(!!event, "Got unexpected NULL event.\n");
/* auto-reset event */ wait_result = WaitForSingleObject(event, 0);