[Mesa-dev] [PATCH v2 4/4] dri/common: clear the loaderPrivate pointer in driDestroyDrawable
Nicolai Hähnle
nhaehnle at gmail.com
Thu Feb 2 17:19:28 UTC 2017
From: Nicolai Hähnle <nicolai.haehnle at amd.com>
The GLX specification says about glXDestroyPixmap:
"The storage for the GLX pixmap will be freed when it is not current
to any client."
We're not really following this language to the letter: some of the storage
is freed immediately (in particular, the dri3_drawable, which contains both
GLXDRIdrawable and loader_dri3_drawable). So we NULL out the pointers to
that freed storage; the previous patches added the corresponding NULL-pointer
checks.
This fixes memory corruption in piglit
./bin/glx-visuals-depth/stencil -pixmap -auto
Cc: 17.0 <mesa-stable at lists.freedesktop.org>
Reviewed-by: Marek Olšák <marek.olsak at amd.com>
---
src/mesa/drivers/dri/common/dri_util.c | 12 ++++++++++++
1 file changed, 12 insertions(+)
diff --git a/src/mesa/drivers/dri/common/dri_util.c b/src/mesa/drivers/dri/common/dri_util.c
index f92eee9..d18c458 100644
--- a/src/mesa/drivers/dri/common/dri_util.c
+++ b/src/mesa/drivers/dri/common/dri_util.c
@@ -638,20 +638,22 @@ static void dri_put_drawable(__DRIdrawable *pdp)
}
}
static __DRIdrawable *
driCreateNewDrawable(__DRIscreen *screen,
const __DRIconfig *config,
void *data)
{
__DRIdrawable *pdraw;
+ assert(data != NULL);
+
pdraw = malloc(sizeof *pdraw);
if (!pdraw)
return NULL;
pdraw->loaderPrivate = data;
pdraw->driScreenPriv = screen;
pdraw->driContextPriv = NULL;
pdraw->refcount = 0;
pdraw->lastStamp = 0;
@@ -667,20 +669,30 @@ driCreateNewDrawable(__DRIscreen *screen,
}
pdraw->dri2.stamp = pdraw->lastStamp + 1;
return pdraw;
}
static void
driDestroyDrawable(__DRIdrawable *pdp)
{
+ /*
+ * The loader's data structures are going away, even if pdp itself stays
+ * around for the time being because it is currently bound. This happens
+ * when a currently bound GLX pixmap is destroyed.
+ *
+ * Clear out the pointer back into the loader's data structures to avoid
+ * accessing an outdated pointer.
+ */
+ pdp->loaderPrivate = NULL;
+
dri_put_drawable(pdp);
}
static __DRIbuffer *
dri2AllocateBuffer(__DRIscreen *screen,
unsigned int attachment, unsigned int format,
int width, int height)
{
return screen->driver->AllocateBuffer(screen, attachment, format,
width, height);
--
2.9.3
More information about the mesa-dev
mailing list