summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorEric Anholt <eric@anholt.net>2014-04-09 10:23:01 -0700
committerEric Anholt <eric@anholt.net>2014-04-23 10:32:15 -0700
commitab6e958a2e611b03e475c16d10beb9961d8dffc8 (patch)
treef3d9479e5c7a89116c6cc516cf2ce22aa63333f6
parentf3f2fb6baac3d2b248eb4b0da13fe95e9dc3de7d (diff)
glx: Make sure that DRI2/swrast calls haven't changed the GL context.
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@anholt.net> Reviewed-by: Michel Dänzer <michel.daenzer@amd.com> Reviewed-by: Adam Jackson <ajax@redhat.com>
-rw-r--r--glx/glxdri2.c61
-rw-r--r--glx/glxdriswrast.c10
2 files changed, 63 insertions, 8 deletions
diff --git a/glx/glxdri2.c b/glx/glxdri2.c
index 94476ddc4..7b368d2d6 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 6fa328831..c30ce9aed 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 = {