summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChris Wilson <chris@chris-wilson.co.uk>2010-06-23 23:56:44 +0100
committerOwain G. Ainsworth <oga@openbsd.org>2010-06-24 20:52:54 +0100
commit62c4ca6663f5984b6a25a9a97fce3b37a00fadbe (patch)
tree1f7530e90852e13f18a154d9943a4ac69d7501b2
parentc4911c5daa5e42745c8e68fbeca42190b1f73084 (diff)
uxa: Fallback to pixman if source is out-of-bounds
If the source is outside the drawable, then CopyArea will fail to initialise the source correctly. The simplest fix in this case is to fallback to pixman to generate the source texture. Fixes: Bug 28497 - Graphics corruption after opening a specific website https://bugs.freedesktop.org/show_bug.cgi?id=28497 Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk> (cherry picked from commit b58a6a39c1568800938eb0e3ebc7664683b61200) Signed-off-by: Owain G. Ainsworth <oga@openbsd.org>
-rw-r--r--uxa/uxa-render.c55
1 files changed, 28 insertions, 27 deletions
diff --git a/uxa/uxa-render.c b/uxa/uxa-render.c
index ed380e91..056b60a4 100644
--- a/uxa/uxa-render.c
+++ b/uxa/uxa-render.c
@@ -720,6 +720,21 @@ uxa_render_picture(ScreenPtr screen,
return picture;
}
+static int
+drawable_contains (DrawablePtr drawable, int x, int y, int w, int h)
+{
+ if (x < 0 || y < 0)
+ return FALSE;
+
+ if (x + w > drawable->width)
+ return FALSE;
+
+ if (y + h > drawable->height)
+ return FALSE;
+
+ return TRUE;
+}
+
PicturePtr
uxa_acquire_drawable(ScreenPtr pScreen,
PicturePtr pSrc,
@@ -729,14 +744,15 @@ uxa_acquire_drawable(ScreenPtr pScreen,
{
PixmapPtr pPixmap;
PicturePtr pDst;
- GCPtr pGC;
int depth, error;
int tx, ty;
+ GCPtr pGC;
depth = pSrc->pDrawable->depth;
- if (depth == 1 ||
- pSrc->filter == PictFilterConvolution || /* XXX */
- !transform_is_integer_translation(pSrc->transform, &tx, &ty)) {
+ if (!transform_is_integer_translation(pSrc->transform, &tx, &ty) ||
+ !drawable_contains(pSrc->pDrawable, x + tx, y + ty, width, height) ||
+ depth == 1 ||
+ pSrc->filter == PictFilterConvolution) {
/* XXX extract the sample extents and do the transformation on the GPU */
pDst = uxa_render_picture(pScreen, pSrc,
pSrc->format | (BitsPerPixel(pSrc->pDrawable->depth) << 24),
@@ -744,7 +760,7 @@ uxa_acquire_drawable(ScreenPtr pScreen,
goto done;
} else {
- if (width == pSrc->pDrawable->width && height == pSrc->pDrawable->depth) {
+ if (width == pSrc->pDrawable->width && height == pSrc->pDrawable->height) {
*out_x = x + pSrc->pDrawable->x;
*out_y = y + pSrc->pDrawable->y;
return pSrc;
@@ -758,7 +774,7 @@ uxa_acquire_drawable(ScreenPtr pScreen,
return 0;
/* Skip the copy if the result remains in memory and not a bo */
- if (!uxa_drawable_is_offscreen(&pPixmap->drawable)) {
+ if (!uxa_pixmap_is_offscreen(pPixmap)) {
pScreen->DestroyPixmap(pPixmap);
return 0;
}
@@ -775,15 +791,15 @@ uxa_acquire_drawable(ScreenPtr pScreen,
FreeScratchGC(pGC);
pDst = CreatePicture(0, &pPixmap->drawable,
- PictureMatchFormat(pScreen, depth, pSrc->format),
- 0, 0, serverClient, &error);
+ PictureMatchFormat(pScreen, depth, pSrc->format),
+ 0, 0, serverClient, &error);
pScreen->DestroyPixmap(pPixmap);
ValidatePicture(pDst);
done:
pDst->componentAlpha = pSrc->componentAlpha;
- *out_x = x;
- *out_y = y;
+ *out_x = 0;
+ *out_y = 0;
return pDst;
}
@@ -803,8 +819,8 @@ uxa_acquire_picture(ScreenPtr screen,
*out_x = x + src->pDrawable->x;
*out_y = y + src->pDrawable->y;
} else {
- *out_x = 0;
- *out_y = 0;
+ *out_x = x;
+ *out_y = y;
}
return src;
}
@@ -1436,21 +1452,6 @@ compatible_formats (CARD8 op, PicturePtr dst, PicturePtr src)
return 0;
}
-static int
-drawable_contains (DrawablePtr drawable, int x, int y, int w, int h)
-{
- if (x < 0 || y < 0)
- return FALSE;
-
- if (x + w > drawable->width)
- return FALSE;
-
- if (y + h > drawable->height)
- return FALSE;
-
- return TRUE;
-}
-
void
uxa_composite(CARD8 op,
PicturePtr pSrc,