From: Dave Airlie <airlied@xxxxxxxxx> This makes X -retro actually render fast, as opposed to glacially slow. Signed-off-by: Dave Airlie <airlied@xxxxxxxxxx> --- src/uxa/uxa-accel.c | 78 ++++++++++++++++++++++++++++++++++++++++++++++------- 1 file changed, 68 insertions(+), 10 deletions(-) diff --git a/src/uxa/uxa-accel.c b/src/uxa/uxa-accel.c index e456e6c..f7c32b7 100644 --- a/src/uxa/uxa-accel.c +++ b/src/uxa/uxa-accel.c @@ -1137,7 +1137,7 @@ uxa_fill_region_tiled(DrawablePtr pDrawable, int nbox = REGION_NUM_RECTS(pRegion); BoxPtr pBox = REGION_RECTS(pRegion); Bool ret = FALSE; - + int i; tileWidth = pTile->drawable.width; tileHeight = pTile->drawable.height; @@ -1157,24 +1157,31 @@ uxa_fill_region_tiled(DrawablePtr pDrawable, !uxa_screen->info->check_copy(pTile, pPixmap, alu, planemask)) return FALSE; - REGION_TRANSLATE(pScreen, pRegion, xoff, yoff); if ((*uxa_screen->info->prepare_copy) (pTile, pPixmap, 1, 1, alu, planemask)) { - while (nbox--) { - int height = pBox->y2 - pBox->y1; - int dstY = pBox->y1; + if (xoff || yoff) + REGION_TRANSLATE(pScreen, pRegion, xoff, yoff); + + for (i = 0; i < nbox; i++) { + int height = pBox[i].y2 - pBox[i].y1; + int dstY = pBox[i].y1; int tileY; + if (alu == GXcopy) + height = min(height, tileHeight); + modulus(dstY - yoff - pDrawable->y - pPatOrg->y, tileHeight, tileY); while (height > 0) { - int width = pBox->x2 - pBox->x1; - int dstX = pBox->x1; + int width = pBox[i].x2 - pBox[i].x1; + int dstX = pBox[i].x1; int tileX; int h = tileHeight - tileY; + if (alu == GXcopy) + width = min(width, tileWidth); if (h > height) h = height; height -= h; @@ -1198,15 +1205,66 @@ uxa_fill_region_tiled(DrawablePtr pDrawable, dstY += h; tileY = 0; } - pBox++; } (*uxa_screen->info->done_copy) (pPixmap); - ret = TRUE; + if (alu != GXcopy) + ret = TRUE; + else { + Bool more_copy = FALSE; + + for (i = 0; i < nbox; i++) { + int dstX = pBox[i].x1 + tileWidth; + int dstY = pBox[i].y1 + tileHeight; + + if ((dstX < pBox[i].x2) || (dstY < pBox[i].y2)) { + more_copy = TRUE; + break; + } + } + + if (more_copy == FALSE) + ret = TRUE; + + if (more_copy && (*uxa_screen->info->prepare_copy) (pPixmap, pPixmap, 1, 1, alu, planemask)) { + for (i = 0; i < nbox; i++) { + int dstX = pBox[i].x1 + tileWidth; + int dstY = pBox[i].y1 + tileHeight; + int width = min(pBox[i].x2 - dstX, tileWidth); + int height = min(pBox[i].y2 - pBox[i].y1, tileHeight); + + while (dstX < pBox[i].x2) { + (*uxa_screen->info->copy) (pPixmap, + pBox[i].x1, pBox[i].y1, + dstX, pBox[i].y1, + width, height); + dstX += width; + width = min(pBox[i].x2 - dstX, width * 2); + } + + width = pBox[i].x2 - pBox[i].x1; + height = min(pBox[i].y2 - dstY, tileHeight); + + while (dstY < pBox[i].y2) { + (*uxa_screen->info->copy) (pPixmap, + pBox[i].x1, pBox[i].y1, + pBox[i].x1, dstY, + width, height); + dstY += height; + height = min(pBox[i].y2 - dstY, height * 2); + } + } + (*uxa_screen->info->done_copy) (pPixmap); + ret = TRUE; + } + } + + if (xoff || yoff) + REGION_TRANSLATE(pScreen, pRegion, -xoff, -yoff); + } out: - REGION_TRANSLATE(pScreen, pRegion, -xoff, -yoff); return ret; } -- 1.8.1.2 _______________________________________________ Spice-devel mailing list Spice-devel@xxxxxxxxxxxxxxxxxxxxx http://lists.freedesktop.org/mailman/listinfo/spice-devel