summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorChris Wilson <chris@chris-wilson.co.uk>2010-09-12 12:34:51 +0100
committerChris Wilson <chris@chris-wilson.co.uk>2010-09-13 01:10:48 +0100
commit08c2caca48323d6d5701dcef3486f850619d7905 (patch)
tree3ae274a3eb25f0ec24870adb75953ba16f399f66
parentae160d7fbfc79e78dad8702efcc55d9c0c25ff67 (diff)
downloadxorg-driver-xf86-video-intel-08c2caca48323d6d5701dcef3486f850619d7905.tar.gz
uxa: Apply source clipping to blits
Yes, this should be done in the higher layers. Yes, I have written code to that. No, it is not ready, hence add the sanity check to the SRC_COPY_BLT. This isn't the first report that I've seen, but will be the last. Bugzilla: https://bugs.freedesktop.org/show_bug.cgi?id=30120 Reported-by: rezbit.hex@gmail.com Signed-off-by: Chris Wilson <chris@chris-wilson.co.uk>
-rw-r--r--src/intel_uxa.c29
1 files changed, 28 insertions, 1 deletions
diff --git a/src/intel_uxa.c b/src/intel_uxa.c
index 0dcd5d32..ef4c553b 100644
--- a/src/intel_uxa.c
+++ b/src/intel_uxa.c
@@ -411,12 +411,39 @@ i830_uxa_copy(PixmapPtr dest, int src_x1, int src_y1, int dst_x1,
ScrnInfoPtr scrn = xf86Screens[dest->drawable.pScreen->myNum];
intel_screen_private *intel = intel_get_screen_private(scrn);
uint32_t cmd;
- int dst_x2, dst_y2;
+ int dst_x2, dst_y2, src_x2, src_y2;
unsigned int dst_pitch, src_pitch;
dst_x2 = dst_x1 + w;
dst_y2 = dst_y1 + h;
+ /* XXX Fixup extents as a lamentable workaround for missing
+ * source clipping in the upper layers.
+ */
+ if (dst_x1 < 0)
+ src_x1 -= dst_x1, dst_x1 = 0;
+ if (dst_y1 < 0)
+ src_y1 -= dst_y1, dst_y1 = 0;
+ if (dst_x2 > dest->drawable.width)
+ dst_x2 = dest->drawable.width;
+ if (dst_y2 > dest->drawable.height)
+ dst_y2 = dest->drawable.height;
+
+ src_x2 = src_x1 + (dst_x2 - dst_x1);
+ src_y2 = src_y1 + (dst_y2 - dst_y1);
+
+ if (src_x1 < 0)
+ dst_x1 -= src_x1, src_x1 = 0;
+ if (src_y1 < 0)
+ dst_y1 -= src_y1, src_y1 = 0;
+ if (src_x2 > intel->render_source->drawable.width)
+ dst_x2 -= src_x2 - intel->render_source->drawable.width;
+ if (src_y2 > intel->render_source->drawable.height)
+ dst_y2 -= src_y2 - intel->render_source->drawable.height;
+
+ if (dst_x2 <= dst_x1 || dst_y2 <= dst_y1)
+ return;
+
dst_pitch = intel_pixmap_pitch(dest);
src_pitch = intel_pixmap_pitch(intel->render_source);