diff options
author | Maarten Maathuis <madman2003@gmail.com> | 2009-04-09 15:45:57 +0200 |
---|---|---|
committer | Maarten Maathuis <madman2003@gmail.com> | 2009-04-10 21:14:47 +0200 |
commit | 1b5758bef0840c6614244e321790231b3c9477c9 (patch) | |
tree | 0bdbe3d9843ccc585bffccb00ad68819506e7673 /exa/exa_accel.c | |
parent | 567cf67959b30432ae30f4851ec17b3a375ab838 (diff) |
exa: implement UTS based upload through CopyArea
- Some image viewers (eog, gqview) trigger the CopyArea path of Xext/shm.c
- I'm not aware of any code path that wouldn't like UTS and trigger this code.
- miDoCopy should handle src coordinate clipping.
- Overlapping blits are obviously not an issue (both would have to be offscreen or not).
Diffstat (limited to 'exa/exa_accel.c')
-rw-r--r-- | exa/exa_accel.c | 70 |
1 files changed, 51 insertions, 19 deletions
diff --git a/exa/exa_accel.c b/exa/exa_accel.c index b1ab2d1d9..d284ff560 100644 --- a/exa/exa_accel.c +++ b/exa/exa_accel.c @@ -466,27 +466,59 @@ exaHWCopyNtoN (DrawablePtr pSrcDrawable, goto fallback; } - if (!exaPixmapIsOffscreen(pSrcPixmap) || - !exaPixmapIsOffscreen(pDstPixmap) || - !(*pExaScr->info->PrepareCopy) (pSrcPixmap, pDstPixmap, reverse ? -1 : 1, - upsidedown ? -1 : 1, - pGC ? pGC->alu : GXcopy, - pGC ? pGC->planemask : FB_ALLONES)) { - goto fallback; - } + if (exaPixmapIsOffscreen(pDstPixmap)) { + /* Normal blitting. */ + if (exaPixmapIsOffscreen(pSrcPixmap)) { + if (!(*pExaScr->info->PrepareCopy) (pSrcPixmap, pDstPixmap, reverse ? -1 : 1, + upsidedown ? -1 : 1, + pGC ? pGC->alu : GXcopy, + pGC ? pGC->planemask : FB_ALLONES)) { + goto fallback; + } - while (nbox--) - { - (*pExaScr->info->Copy) (pDstPixmap, - pbox->x1 + dx + src_off_x, - pbox->y1 + dy + src_off_y, - pbox->x1 + dst_off_x, pbox->y1 + dst_off_y, - pbox->x2 - pbox->x1, pbox->y2 - pbox->y1); - pbox++; - } + while (nbox--) + { + (*pExaScr->info->Copy) (pDstPixmap, + pbox->x1 + dx + src_off_x, + pbox->y1 + dy + src_off_y, + pbox->x1 + dst_off_x, pbox->y1 + dst_off_y, + pbox->x2 - pbox->x1, pbox->y2 - pbox->y1); + pbox++; + } + + (*pExaScr->info->DoneCopy) (pDstPixmap); + exaMarkSync (pDstDrawable->pScreen); + /* UTS: mainly for SHM PutImage's secondary path. */ + } else { + int bpp = pSrcDrawable->bitsPerPixel; + int src_stride = exaGetPixmapPitch(pSrcPixmap); + CARD8 *src = NULL; - (*pExaScr->info->DoneCopy) (pDstPixmap); - exaMarkSync (pDstDrawable->pScreen); + if (!pExaScr->info->UploadToScreen) + goto fallback; + + if (pSrcDrawable->bitsPerPixel != pDstDrawable->bitsPerPixel) + goto fallback; + + if (pSrcDrawable->bitsPerPixel < 8) + goto fallback; + + if (pGC && !(pGC->alu == GXcopy && EXA_PM_IS_SOLID(pSrcDrawable, pGC->planemask))) + goto fallback; + + while (nbox--) + { + src = pSrcExaPixmap->sys_ptr + (pbox->y1 + dy + src_off_y) * src_stride + (pbox->x1 + dx + src_off_x) * (bpp / 8); + if (!pExaScr->info->UploadToScreen(pDstPixmap, pbox->x1 + dst_off_x, + pbox->y1 + dst_off_y, pbox->x2 - pbox->x1, pbox->y2 - pbox->y1, + (char *) src, src_stride)) + goto fallback; + + pbox++; + } + } + } else + goto fallback; goto out; |