xf86-video-intel: 2 commits - src/sna/gen6_render.c src/sna/gen7_render.c src/sna/sna_render.c src/sna/sna_render.h
Chris Wilson
ickle at kemper.freedesktop.org
Sat Aug 4 03:23:42 PDT 2012
src/sna/gen6_render.c | 73 +++++++++++++++++++++++++---------------
src/sna/gen7_render.c | 91 +++++++++++++++++++++-----------------------------
src/sna/sna_render.c | 37 ++++++++++++++++++++
src/sna/sna_render.h | 6 +++
4 files changed, 129 insertions(+), 78 deletions(-)
New commits:
commit 20e58077fe071fd03d44a97194aa163376dc46a4
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date: Sat Aug 4 11:21:10 2012 +0100
sna/gen6: Reduce ring switching for overlapping copy boxes
Signed-off-by: Chris Wilson <chris at chris-wilson.co.uk>
diff --git a/src/sna/gen6_render.c b/src/sna/gen6_render.c
index 19b8a2d..1d51300 100644
--- a/src/sna/gen6_render.c
+++ b/src/sna/gen6_render.c
@@ -3243,34 +3243,33 @@ static inline bool prefer_blt_copy(struct sna *sna,
}
static inline bool
-overlaps(struct kgem_bo *src_bo, int16_t src_dx, int16_t src_dy,
+overlaps(struct sna *sna,
+ struct kgem_bo *src_bo, int16_t src_dx, int16_t src_dy,
struct kgem_bo *dst_bo, int16_t dst_dx, int16_t dst_dy,
- const BoxRec *box, int n)
+ const BoxRec *box, int n, BoxRec *extents)
{
- BoxRec extents;
-
if (src_bo != dst_bo)
return false;
- extents = box[0];
+ *extents = box[0];
while (--n) {
box++;
- if (box->x1 < extents.x1)
- extents.x1 = box->x1;
- if (box->x2 > extents.x2)
- extents.x2 = box->x2;
+ if (box->x1 < extents->x1)
+ extents->x1 = box->x1;
+ if (box->x2 > extents->x2)
+ extents->x2 = box->x2;
- if (box->y1 < extents.y1)
- extents.y1 = box->y1;
- if (box->y2 > extents.y2)
- extents.y2 = box->y2;
+ if (box->y1 < extents->y1)
+ extents->y1 = box->y1;
+ if (box->y2 > extents->y2)
+ extents->y2 = box->y2;
}
- return (extents.x2 + src_dx > extents.x1 + dst_dx &&
- extents.x1 + src_dx < extents.x2 + dst_dx &&
- extents.y2 + src_dy > extents.y1 + dst_dy &&
- extents.y1 + src_dy < extents.y2 + dst_dy);
+ return (extents->x2 + src_dx > extents->x1 + dst_dx &&
+ extents->x1 + src_dx < extents->x2 + dst_dx &&
+ extents->y2 + src_dy > extents->y1 + dst_dy &&
+ extents->y1 + src_dy < extents->y2 + dst_dy);
}
static bool
@@ -3280,13 +3279,14 @@ gen6_render_copy_boxes(struct sna *sna, uint8_t alu,
const BoxRec *box, int n, unsigned flags)
{
struct sna_composite_op tmp;
+ BoxRec extents;
DBG(("%s (%d, %d)->(%d, %d) x %d, alu=%x, self-copy=%d, overlaps? %d\n",
__FUNCTION__, src_dx, src_dy, dst_dx, dst_dy, n, alu,
src_bo == dst_bo,
overlaps(src_bo, src_dx, src_dy,
dst_bo, dst_dx, dst_dy,
- box, n)));
+ box, n, &extents)));
if (prefer_blt_copy(sna, src, src_bo, dst, dst_bo, flags) &&
sna_blt_compare_depth(&src->drawable, &dst->drawable) &&
@@ -3297,18 +3297,37 @@ gen6_render_copy_boxes(struct sna *sna, uint8_t alu,
box, n))
return true;
- if (!(alu == GXcopy || alu == GXclear) ||
- overlaps(src_bo, src_dx, src_dy,
- dst_bo, dst_dx, dst_dy,
- box, n)) {
+ if (!(alu == GXcopy || alu == GXclear)) {
fallback_blt:
if (!sna_blt_compare_depth(&src->drawable, &dst->drawable))
return false;
return sna_blt_copy_boxes_fallback(sna, alu,
- src, src_bo, src_dx, src_dy,
- dst, dst_bo, dst_dx, dst_dy,
- box, n);
+ src, src_bo, src_dx, src_dy,
+ dst, dst_bo, dst_dx, dst_dy,
+ box, n);
+ }
+
+ if (overlaps(sna,
+ src_bo, src_dx, src_dy,
+ dst_bo, dst_dx, dst_dy,
+ box, n, &extents)) {
+ if (too_large(extents.x2-extents.x1, extents.y2-extents.y1))
+ goto fallback_blt;
+
+ if ((flags & COPY_LAST || can_switch_rings(sna)) &&
+ sna_blt_compare_depth(&src->drawable, &dst->drawable) &&
+ sna_blt_copy_boxes(sna, alu,
+ src_bo, src_dx, src_dy,
+ dst_bo, dst_dx, dst_dy,
+ dst->drawable.bitsPerPixel,
+ box, n))
+ return true;
+
+ return sna_render_copy_boxes__overlap(sna, alu,
+ src, src_bo, src_dx, src_dy,
+ dst, dst_bo, dst_dx, dst_dy,
+ box, n, &extents);
}
if (dst->drawable.depth == src->drawable.depth) {
@@ -3330,9 +3349,9 @@ fallback_blt:
sna_render_composite_redirect_init(&tmp);
if (too_large(tmp.dst.width, tmp.dst.height)) {
- BoxRec extents = box[0];
int i;
+ extents = box[0];
for (i = 1; i < n; i++) {
if (box[i].x1 < extents.x1)
extents.x1 = box[i].x1;
@@ -3360,9 +3379,9 @@ fallback_blt:
tmp.src.card_format = gen6_get_card_format(tmp.src.pict_format);
if (too_large(src->drawable.width, src->drawable.height)) {
- BoxRec extents = box[0];
int i;
+ extents = box[0];
for (i = 1; i < n; i++) {
if (extents.x1 < box[i].x1)
extents.x1 = box[i].x1;
commit 2345227663f443baa3c30bdf8b8c33827b7f4947
Author: Chris Wilson <chris at chris-wilson.co.uk>
Date: Sat Aug 4 11:12:12 2012 +0100
sna/gen7: Use a temporary to avoid switching rings for overlapping copies
Signed-off-by: Chris Wilson <chris at chris-wilson.co.uk>
diff --git a/src/sna/gen7_render.c b/src/sna/gen7_render.c
index 9ef5e17..954e42f 100644
--- a/src/sna/gen7_render.c
+++ b/src/sna/gen7_render.c
@@ -3332,35 +3332,30 @@ static inline bool
overlaps(struct sna *sna,
struct kgem_bo *src_bo, int16_t src_dx, int16_t src_dy,
struct kgem_bo *dst_bo, int16_t dst_dx, int16_t dst_dy,
- const BoxRec *box, int n)
+ const BoxRec *box, int n, BoxRec *extents)
{
- BoxRec extents;
-
if (src_bo != dst_bo)
return false;
- if (can_switch_rings(sna))
- return true;
-
- extents = box[0];
+ *extents = box[0];
while (--n) {
box++;
- if (box->x1 < extents.x1)
- extents.x1 = box->x1;
- if (box->x2 > extents.x2)
- extents.x2 = box->x2;
+ if (box->x1 < extents->x1)
+ extents->x1 = box->x1;
+ if (box->x2 > extents->x2)
+ extents->x2 = box->x2;
- if (box->y1 < extents.y1)
- extents.y1 = box->y1;
- if (box->y2 > extents.y2)
- extents.y2 = box->y2;
+ if (box->y1 < extents->y1)
+ extents->y1 = box->y1;
+ if (box->y2 > extents->y2)
+ extents->y2 = box->y2;
}
- return (extents.x2 + src_dx > extents.x1 + dst_dx &&
- extents.x1 + src_dx < extents.x2 + dst_dx &&
- extents.y2 + src_dy > extents.y1 + dst_dy &&
- extents.y1 + src_dy < extents.y2 + dst_dy);
+ return (extents->x2 + src_dx > extents->x1 + dst_dx &&
+ extents->x1 + src_dx < extents->x2 + dst_dx &&
+ extents->y2 + src_dy > extents->y1 + dst_dy &&
+ extents->y1 + src_dy < extents->y2 + dst_dy);
}
static bool
@@ -3370,6 +3365,7 @@ gen7_render_copy_boxes(struct sna *sna, uint8_t alu,
const BoxRec *box, int n, unsigned flags)
{
struct sna_composite_op tmp;
+ BoxRec extents;
DBG(("%s (%d, %d)->(%d, %d) x %d, alu=%x, self-copy=%d, overlaps? %d\n",
__FUNCTION__, src_dx, src_dy, dst_dx, dst_dy, n, alu,
@@ -3377,7 +3373,7 @@ gen7_render_copy_boxes(struct sna *sna, uint8_t alu,
overlaps(sna,
src_bo, src_dx, src_dy,
dst_bo, dst_dx, dst_dy,
- box, n)));
+ box, n, &extents)));
if (prefer_blt_copy(sna, src, src_bo, dst, dst_bo, flags) &&
sna_blt_compare_depth(&src->drawable, &dst->drawable) &&
@@ -3388,44 +3384,37 @@ gen7_render_copy_boxes(struct sna *sna, uint8_t alu,
box, n))
return true;
- if (too_large(dst->drawable.width, dst->drawable.height) ||
- sna_blt_compare_depth(&src->drawable, &dst->drawable)) {
- BoxRec extents = box[0];
- int i;
+ if (!(alu == GXcopy || alu == GXclear)) {
+fallback_blt:
+ if (!sna_blt_compare_depth(&src->drawable, &dst->drawable))
+ return false;
- for (i = 1; i < n; i++) {
- if (box[i].x1 < extents.x1)
- extents.x1 = box[i].x1;
- if (box[i].y1 < extents.y1)
- extents.y1 = box[i].y1;
+ return sna_blt_copy_boxes_fallback(sna, alu,
+ src, src_bo, src_dx, src_dy,
+ dst, dst_bo, dst_dx, dst_dy,
+ box, n);
+ }
- if (box[i].x2 > extents.x2)
- extents.x2 = box[i].x2;
- if (box[i].y2 > extents.y2)
- extents.y2 = box[i].y2;
- }
- if (too_large(extents.x2 - extents.x1, extents.y2 - extents.y1) &&
+ if (overlaps(sna,
+ src_bo, src_dx, src_dy,
+ dst_bo, dst_dx, dst_dy,
+ box, n, &extents)) {
+ if (too_large(extents.x2-extents.x1, extents.y2-extents.y1))
+ goto fallback_blt;
+
+ if ((flags & COPY_LAST || can_switch_rings(sna)) &&
+ sna_blt_compare_depth(&src->drawable, &dst->drawable) &&
sna_blt_copy_boxes(sna, alu,
src_bo, src_dx, src_dy,
dst_bo, dst_dx, dst_dy,
dst->drawable.bitsPerPixel,
box, n))
return true;
- }
- if (!(alu == GXcopy || alu == GXclear) ||
- overlaps(sna,
- src_bo, src_dx, src_dy,
- dst_bo, dst_dx, dst_dy,
- box, n)) {
-fallback_blt:
- if (!sna_blt_compare_depth(&src->drawable, &dst->drawable))
- return false;
-
- return sna_blt_copy_boxes_fallback(sna, alu,
- src, src_bo, src_dx, src_dy,
- dst, dst_bo, dst_dx, dst_dy,
- box, n);
+ return sna_render_copy_boxes__overlap(sna, alu,
+ src, src_bo, src_dx, src_dy,
+ dst, dst_bo, dst_dx, dst_dy,
+ box, n, &extents);
}
if (dst->drawable.depth == src->drawable.depth) {
@@ -3447,9 +3436,9 @@ fallback_blt:
sna_render_composite_redirect_init(&tmp);
if (too_large(tmp.dst.width, tmp.dst.height)) {
- BoxRec extents = box[0];
int i;
+ extents = box[0];
for (i = 1; i < n; i++) {
if (box[i].x1 < extents.x1)
extents.x1 = box[i].x1;
@@ -3477,9 +3466,9 @@ fallback_blt:
tmp.src.card_format = gen7_get_card_format(tmp.src.pict_format);
if (too_large(src->drawable.width, src->drawable.height)) {
- BoxRec extents = box[0];
int i;
+ extents = box[0];
for (i = 1; i < n; i++) {
if (extents.x1 < box[i].x1)
extents.x1 = box[i].x1;
diff --git a/src/sna/sna_render.c b/src/sna/sna_render.c
index 9d4b926..f507f49 100644
--- a/src/sna/sna_render.c
+++ b/src/sna/sna_render.c
@@ -1950,3 +1950,40 @@ sna_render_composite_redirect_done(struct sna *sna,
kgem_bo_destroy(&sna->kgem, op->dst.bo);
}
}
+
+bool
+sna_render_copy_boxes__overlap(struct sna *sna, uint8_t alu,
+ PixmapPtr src, struct kgem_bo *src_bo, int16_t src_dx, int16_t src_dy,
+ PixmapPtr dst, struct kgem_bo *dst_bo, int16_t dst_dx, int16_t dst_dy,
+ const BoxRec *box, int n, const BoxRec *extents)
+{
+ ScreenPtr screen = dst->drawable.pScreen;
+ struct kgem_bo *bo;
+ PixmapPtr tmp;
+ bool ret = false;
+
+ tmp = screen->CreatePixmap(screen,
+ extents->x2 - extents->x1,
+ extents->y2 - extents->y1,
+ dst->drawable.depth,
+ SNA_CREATE_SCRATCH);
+ if (tmp == NULL)
+ return false;
+
+ bo = sna_pixmap_get_bo(tmp);
+ if (bo == NULL)
+ goto out;
+
+ ret = (sna->render.copy_boxes(sna, alu,
+ src, src_bo, src_dx, src_dy,
+ tmp, bo, -extents->x1, -extents->y1,
+ box, n , 0) &&
+ sna->render.copy_boxes(sna, alu,
+ tmp, bo, -extents->x1, -extents->y1,
+ dst, dst_bo, dst_dx, dst_dy,
+ box, n , 0));
+
+out:
+ screen->DestroyPixmap(tmp);
+ return ret;
+}
diff --git a/src/sna/sna_render.h b/src/sna/sna_render.h
index 68bb901..a2bcb45 100644
--- a/src/sna/sna_render.h
+++ b/src/sna/sna_render.h
@@ -704,6 +704,12 @@ sna_render_composite_redirect_done(struct sna *sna,
const struct sna_composite_op *op);
bool
+sna_render_copy_boxes__overlap(struct sna *sna, uint8_t alu,
+ PixmapPtr src, struct kgem_bo *src_bo, int16_t src_dx, int16_t src_dy,
+ PixmapPtr dst, struct kgem_bo *dst_bo, int16_t dst_dx, int16_t dst_dy,
+ const BoxRec *box, int n, const BoxRec *extents);
+
+bool
sna_composite_mask_is_opaque(PicturePtr mask);
#endif /* SNA_RENDER_H */
More information about the xorg-commit
mailing list