[PATCH 3/5] wined3d: Ensure draw ordering across contexts.

Henri Verbeet hverbeet at codeweavers.com
Wed Jan 27 13:19:40 CST 2010


---
 dlls/wined3d/device.c   |   14 +++++++-------
 dlls/wined3d/drawprim.c |    3 +++
 dlls/wined3d/surface.c  |   30 +++++++++++++++++++-----------
 3 files changed, 29 insertions(+), 18 deletions(-)

diff --git a/dlls/wined3d/device.c b/dlls/wined3d/device.c
index d66b46e..8e85e4d 100644
--- a/dlls/wined3d/device.c
+++ b/dlls/wined3d/device.c
@@ -4135,7 +4135,6 @@ HRESULT IWineD3DDeviceImpl_ClearSurface(IWineD3DDeviceImpl *This,  IWineD3DSurfa
     const WINED3DVIEWPORT *vp = &This->stateBlock->viewport;
     UINT drawable_width, drawable_height;
     IWineD3DSurfaceImpl *depth_stencil = (IWineD3DSurfaceImpl *) This->stencilBufferTarget;
-    IWineD3DSwapChainImpl *swapchain = NULL;
     struct wined3d_context *context;
 
     /* When we're clearing parts of the drawable, make sure that the target surface is well up to date in the
@@ -4305,12 +4304,7 @@ HRESULT IWineD3DDeviceImpl_ClearSurface(IWineD3DDeviceImpl *This,  IWineD3DSurfa
 
     LEAVE_GL();
 
-    if (SUCCEEDED(IWineD3DSurface_GetContainer((IWineD3DSurface *)target, &IID_IWineD3DSwapChain, (void **)&swapchain))) {
-        if (target == (IWineD3DSurfaceImpl*) swapchain->frontBuffer) {
-            wglFlush();
-        }
-        IWineD3DSwapChain_Release((IWineD3DSwapChain *) swapchain);
-    }
+    wglFlush(); /* Flush to ensure ordering across contexts. */
 
     context_release(context);
 
@@ -5315,6 +5309,9 @@ static void color_fill_fbo(IWineD3DDevice *iface, IWineD3DSurface *surface,
     checkGLcall("glClear");
 
     LEAVE_GL();
+
+    wglFlush(); /* Flush to ensure ordering across contexts. */
+
     context_release(context);
 }
 
@@ -5768,6 +5765,9 @@ void stretch_rect_fbo(IWineD3DDevice *iface, IWineD3DSurface *src_surface, WINED
     }
 
     LEAVE_GL();
+
+    wglFlush(); /* Flush to ensure ordering across contexts. */
+
     context_release(context);
 
     IWineD3DSurface_ModifyLocation(dst_surface, SFLAG_INDRAWABLE, TRUE);
diff --git a/dlls/wined3d/drawprim.c b/dlls/wined3d/drawprim.c
index 8250e79..b29d012 100644
--- a/dlls/wined3d/drawprim.c
+++ b/dlls/wined3d/drawprim.c
@@ -690,6 +690,9 @@ void drawPrimitive(IWineD3DDevice *iface, UINT index_count, UINT StartIdx, UINT
 
     /* Finished updating the screen, restore lock */
     LEAVE_GL();
+
+    wglFlush(); /* Flush to ensure ordering across contexts. */
+
     context_release(context);
 
     TRACE("Done all gl drawing\n");
diff --git a/dlls/wined3d/surface.c b/dlls/wined3d/surface.c
index 8dcc691..233f079 100644
--- a/dlls/wined3d/surface.c
+++ b/dlls/wined3d/surface.c
@@ -3447,6 +3447,9 @@ static inline void fb_copy_to_texture_hwstretch(IWineD3DSurfaceImpl *This, IWine
     }
 
     LEAVE_GL();
+
+    wglFlush(); /* Flush to ensure ordering across contexts. */
+
     context_release(context);
 
     /* The texture is now most up to date - If the surface is a render target and has a drawable, this
@@ -3921,9 +3924,7 @@ static HRESULT IWineD3DSurfaceImpl_BltOverride(IWineD3DSurfaceImpl *This, const
         /* Leave the opengl state valid for blitting */
         myDevice->blitter->unset_shader((IWineD3DDevice *) myDevice);
 
-        /* Flush in case the drawable is used by multiple GL contexts */
-        if(dstSwapchain && (This == (IWineD3DSurfaceImpl *) dstSwapchain->frontBuffer || dstSwapchain->num_contexts >= 2))
-            wglFlush();
+        wglFlush(); /* Flush to ensure ordering across contexts. */
 
         context_release(context);
 
@@ -4552,7 +4553,11 @@ void surface_load_ds_location(IWineD3DSurface *iface, struct wined3d_context *co
             else context_bind_fbo(context, GL_FRAMEBUFFER, NULL);
 
             LEAVE_GL();
-        } else {
+
+            wglFlush(); /* Flush to ensure ordering across contexts. */
+        }
+        else
+        {
             FIXME("No up to date depth stencil location\n");
         }
     } else if (location == SFLAG_DS_ONSCREEN) {
@@ -4569,7 +4574,11 @@ void surface_load_ds_location(IWineD3DSurface *iface, struct wined3d_context *co
             if (context->current_fbo) context_bind_fbo(context, GL_FRAMEBUFFER, &context->current_fbo->id);
 
             LEAVE_GL();
-        } else {
+
+            wglFlush(); /* Flush to ensure ordering across contexts. */
+        }
+        else
+        {
             FIXME("No up to date depth stencil location\n");
         }
     } else {
@@ -4802,15 +4811,14 @@ static inline void surface_blt_to_drawable(IWineD3DSurfaceImpl *This, const RECT
 
     LEAVE_GL();
 
+    wglFlush(); /* Flush to ensure ordering across contexts. */
+
     if(SUCCEEDED(IWineD3DSurface_GetContainer((IWineD3DSurface*)This, &IID_IWineD3DSwapChain, (void **) &swapchain)))
     {
-        /* Make sure to flush the buffers. This is needed in apps like Red Alert II and Tiberian SUN that use multiple WGL contexts. */
-        if(((IWineD3DSwapChainImpl*)swapchain)->frontBuffer == (IWineD3DSurface*)This ||
-           ((IWineD3DSwapChainImpl*)swapchain)->num_contexts >= 2)
-            wglFlush();
-
         IWineD3DSwapChain_Release(swapchain);
-    } else {
+    }
+    else
+    {
         /* We changed the filtering settings on the texture. Inform the container about this to get the filters
          * reset properly next draw
          */
-- 
1.6.4.4




More information about the wine-patches mailing list