[PATCH 06/12] glx: Make sure that DRI2/swrast calls haven't changed the GL context.

Eric Anholt eric at anholt.net
Fri Apr 18 11:40:04 PDT 2014


These functions are called from the GL driver, in some series of GL
calls by GLX.  If some server component (like glamor CreatePixmap for
GetBuffers()) changes the GL context on us, we need to set it back or
the later GL calls will land in the glamor context instead of the GLX
context.

Signed-off-by: Eric Anholt <eric at anholt.net>
---
 glx/glxdri2.c      | 61 +++++++++++++++++++++++++++++++++++++++++++++++-------
 glx/glxdriswrast.c | 10 +++++++++
 2 files changed, 63 insertions(+), 8 deletions(-)

diff --git a/glx/glxdri2.c b/glx/glxdri2.c
index 94476dd..7b368d2 100644
--- a/glx/glxdri2.c
+++ b/glx/glxdri2.c
@@ -121,6 +121,7 @@ copy_box(__GLXdrawable * drawable,
 {
     BoxRec box;
     RegionRec region;
+    __GLXcontext *cx = lastGLContext;
 
     box.x1 = x;
     box.y1 = y;
@@ -129,6 +130,10 @@ copy_box(__GLXdrawable * drawable,
     RegionInit(&region, &box, 0);
 
     DRI2CopyRegion(drawable->pDraw, &region, dst, src);
+    if (cx != lastGLContext) {
+        lastGLContext = cx;
+        cx->makeCurrent(cx);
+    }
 }
 
 static void
@@ -198,26 +203,37 @@ __glXDRIdrawableSwapBuffers(ClientPtr client, __GLXdrawable * drawable)
     __GLXDRIdrawable *priv = (__GLXDRIdrawable *) drawable;
     __GLXDRIscreen *screen = priv->screen;
     CARD64 unused;
+    __GLXcontext *cx = lastGLContext;
+    int status;
 
     if (screen->flush) {
         (*screen->flush->flush) (priv->driDrawable);
         (*screen->flush->invalidate) (priv->driDrawable);
     }
 
-    if (DRI2SwapBuffers(client, drawable->pDraw, 0, 0, 0, &unused,
-                        __glXdriSwapEvent, drawable) != Success)
-        return FALSE;
+    status = DRI2SwapBuffers(client, drawable->pDraw, 0, 0, 0, &unused,
+                             __glXdriSwapEvent, drawable);
+    if (cx != lastGLContext) {
+        lastGLContext = cx;
+        cx->makeCurrent(cx);
+    }
 
-    return TRUE;
+    return status == Success;
 }
 
 static int
 __glXDRIdrawableSwapInterval(__GLXdrawable * drawable, int interval)
 {
+    __GLXcontext *cx = lastGLContext;
+
     if (interval <= 0)          /* || interval > BIGNUM? */
         return GLX_BAD_VALUE;
 
     DRI2SwapInterval(drawable->pDraw, interval);
+    if (cx != lastGLContext) {
+        lastGLContext = cx;
+        cx->makeCurrent(cx);
+    }
 
     return 0;
 }
@@ -270,7 +286,16 @@ static Bool
 __glXDRIcontextWait(__GLXcontext * baseContext,
                     __GLXclientState * cl, int *error)
 {
-    if (DRI2WaitSwap(cl->client, baseContext->drawPriv->pDraw)) {
+    __GLXcontext *cx = lastGLContext;
+    Bool ret;
+
+    ret = DRI2WaitSwap(cl->client, baseContext->drawPriv->pDraw);
+    if (cx != lastGLContext) {
+        lastGLContext = cx;
+        cx->makeCurrent(cx);
+    }
+
+    if (ret) {
         *error = cl->client->noClientException;
         return TRUE;
     }
@@ -594,6 +619,8 @@ __glXDRIscreenCreateDrawable(ClientPtr client,
     __GLXDRIscreen *driScreen = (__GLXDRIscreen *) screen;
     __GLXDRIconfig *config = (__GLXDRIconfig *) glxConfig;
     __GLXDRIdrawable *private;
+    __GLXcontext *cx = lastGLContext;
+    Bool ret;
 
     private = calloc(1, sizeof *private);
     if (private == NULL)
@@ -612,9 +639,15 @@ __glXDRIscreenCreateDrawable(ClientPtr client,
     private->base.waitGL = __glXDRIdrawableWaitGL;
     private->base.waitX = __glXDRIdrawableWaitX;
 
-    if (DRI2CreateDrawable2(client, pDraw, drawId,
-                            __glXDRIinvalidateBuffers, private,
-                            &private->dri2_id)) {
+    ret = DRI2CreateDrawable2(client, pDraw, drawId,
+                              __glXDRIinvalidateBuffers, private,
+                              &private->dri2_id);
+    if (cx != lastGLContext) {
+        lastGLContext = cx;
+        cx->makeCurrent(cx);
+    }
+
+    if (ret) {
         free(private);
         return NULL;
     }
@@ -636,9 +669,15 @@ dri2GetBuffers(__DRIdrawable * driDrawable,
     DRI2BufferPtr *buffers;
     int i;
     int j;
+    __GLXcontext *cx = lastGLContext;
 
     buffers = DRI2GetBuffers(private->base.pDraw,
                              width, height, attachments, count, out_count);
+    if (cx != lastGLContext) {
+        lastGLContext = cx;
+        cx->makeCurrent(cx);
+    }
+
     if (*out_count > MAX_DRAWABLE_BUFFERS) {
         *out_count = 0;
         return NULL;
@@ -680,10 +719,16 @@ dri2GetBuffersWithFormat(__DRIdrawable * driDrawable,
     DRI2BufferPtr *buffers;
     int i;
     int j = 0;
+    __GLXcontext *cx = lastGLContext;
 
     buffers = DRI2GetBuffersWithFormat(private->base.pDraw,
                                        width, height, attachments, count,
                                        out_count);
+    if (cx != lastGLContext) {
+        lastGLContext = cx;
+        cx->makeCurrent(cx);
+    }
+
     if (*out_count > MAX_DRAWABLE_BUFFERS) {
         *out_count = 0;
         return NULL;
diff --git a/glx/glxdriswrast.c b/glx/glxdriswrast.c
index 6fa3288..c30ce9a 100644
--- a/glx/glxdriswrast.c
+++ b/glx/glxdriswrast.c
@@ -337,6 +337,7 @@ swrastPutImage(__DRIdrawable * draw, int op,
     __GLXDRIdrawable *drawable = loaderPrivate;
     DrawablePtr pDraw = drawable->base.pDraw;
     GCPtr gc;
+    __GLXcontext *cx = lastGLContext;
 
     switch (op) {
     case __DRI_SWRAST_IMAGE_OP_DRAW:
@@ -352,6 +353,10 @@ swrastPutImage(__DRIdrawable * draw, int op,
     ValidateGC(pDraw, gc);
 
     gc->ops->PutImage(pDraw, gc, pDraw->depth, x, y, w, h, 0, ZPixmap, data);
+    if (cx != lastGLContext) {
+        lastGLContext = cx;
+        cx->makeCurrent(cx);
+    }
 }
 
 static void
@@ -361,8 +366,13 @@ swrastGetImage(__DRIdrawable * draw,
     __GLXDRIdrawable *drawable = loaderPrivate;
     DrawablePtr pDraw = drawable->base.pDraw;
     ScreenPtr pScreen = pDraw->pScreen;
+    __GLXcontext *cx = lastGLContext;
 
     pScreen->GetImage(pDraw, x, y, w, h, ZPixmap, ~0L, data);
+    if (cx != lastGLContext) {
+        lastGLContext = cx;
+        cx->makeCurrent(cx);
+    }
 }
 
 static const __DRIswrastLoaderExtension swrastLoaderExtension = {
-- 
1.9.2



More information about the xorg-devel mailing list