diff --git a/dlls/wined3d/context.c b/dlls/wined3d/context.c index f3566cfc135..a604088ea37 100644 --- a/dlls/wined3d/context.c +++ b/dlls/wined3d/context.c @@ -844,25 +844,9 @@ static void context_update_window(struct wined3d_context *context) context, context->win_handle, context->swapchain->win_handle); if (context->valid) - { - /* You'd figure ReleaseDC() would fail if the DC doesn't match the - * window. However, that's not what actually happens, and there are - * user32 tests that confirm ReleaseDC() with the wrong window is - * supposed to succeed. So explicitly check that the DC belongs to - * the window, since we want to avoid releasing a DC that belongs to - * some other window if the original window was already destroyed. */ - if (WindowFromDC(context->hdc) != context->win_handle) - { - WARN("DC %p does not belong to window %p.\n", - context->hdc, context->win_handle); - } - else if (!ReleaseDC(context->win_handle, context->hdc)) - { - ERR("Failed to release device context %p, last error %#x.\n", - context->hdc, GetLastError()); - } - } - else context->valid = 1; + wined3d_release_dc(context->win_handle, context->hdc); + else + context->valid = 1; context->win_handle = context->swapchain->win_handle; @@ -987,7 +971,7 @@ static void context_destroy_gl_resources(struct wined3d_context *context) ERR("Failed to disable GL context.\n"); } - ReleaseDC(context->win_handle, context->hdc); + wined3d_release_dc(context->win_handle, context->hdc); if (!wglDeleteContext(context->glCtx)) { diff --git a/dlls/wined3d/directx.c b/dlls/wined3d/directx.c index 7d4f859ffd3..31ff52acb8e 100644 --- a/dlls/wined3d/directx.c +++ b/dlls/wined3d/directx.c @@ -277,7 +277,7 @@ static void wined3d_caps_gl_ctx_destroy(const struct wined3d_caps_gl_ctx *ctx) ERR("wglDeleteContext(%p) failed, last error %#x.\n", ctx->gl_ctx, err); } - ReleaseDC(ctx->wnd, ctx->dc); + wined3d_release_dc(ctx->wnd, ctx->dc); DestroyWindow(ctx->wnd); if (ctx->restore_gl_ctx && !wglMakeCurrent(ctx->restore_dc, ctx->restore_gl_ctx)) diff --git a/dlls/wined3d/swapchain.c b/dlls/wined3d/swapchain.c index 73243a98d94..7a383fdc543 100644 --- a/dlls/wined3d/swapchain.c +++ b/dlls/wined3d/swapchain.c @@ -83,7 +83,7 @@ static void swapchain_cleanup(struct wined3d_swapchain *swapchain) { TRACE("Destroying backup wined3d window %p, dc %p.\n", swapchain->backup_wnd, swapchain->backup_dc); - ReleaseDC(swapchain->backup_wnd, swapchain->backup_dc); + wined3d_release_dc(swapchain->backup_wnd, swapchain->backup_dc); DestroyWindow(swapchain->backup_wnd); } } diff --git a/dlls/wined3d/utils.c b/dlls/wined3d/utils.c index 3fb6090ae51..f6d3a4483f5 100644 --- a/dlls/wined3d/utils.c +++ b/dlls/wined3d/utils.c @@ -3852,3 +3852,17 @@ void wined3d_ftoa(float value, char *s) sprintf(s, "%s%d.%08de%+03d", sign, x, frac, exponent); } + +void wined3d_release_dc(HWND window, HDC dc) +{ + /* You'd figure ReleaseDC() would fail if the DC doesn't match the window. + * However, that's not what actually happens, and there are user32 tests + * that confirm ReleaseDC() with the wrong window is supposed to succeed. + * So explicitly check that the DC belongs to the window, since we want to + * avoid releasing a DC that belongs to some other window if the original + * window was already destroyed. */ + if (WindowFromDC(dc) != window) + WARN("DC %p does not belong to window %p.\n", dc, window); + else if (!ReleaseDC(window, dc)) + ERR("Failed to release device context %p, last error %#x.\n", dc, GetLastError()); +} diff --git a/dlls/wined3d/wined3d_private.h b/dlls/wined3d/wined3d_private.h index fc92e532410..e4ce84db1d2 100644 --- a/dlls/wined3d/wined3d_private.h +++ b/dlls/wined3d/wined3d_private.h @@ -2742,6 +2742,8 @@ void multiply_matrix(struct wined3d_matrix *dest, const struct wined3d_matrix *s UINT wined3d_log2i(UINT32 x) DECLSPEC_HIDDEN; unsigned int count_bits(unsigned int mask) DECLSPEC_HIDDEN; +void wined3d_release_dc(HWND window, HDC dc) DECLSPEC_HIDDEN; + struct wined3d_shader_lconst { struct list entry;