EXA: Improvements for 1x1 pixmaps.

Initialize system and FB copy in exaFillRegionSolid and adapt
exaGetPixmapFirstPixel to the new migration infrastructure.

This should mostly eliminate migration overhead for these, whether they are
used for acceleration or fallbacks.
This commit is contained in:
Michel Dänzer 2007-08-30 13:44:20 +02:00
parent 489bc7551f
commit 1f457ff3db
2 changed files with 49 additions and 9 deletions

View File

@ -1012,8 +1012,6 @@ exaFillRegionSolid (DrawablePtr pDrawable,
PixmapPtr pPixmap;
int xoff, yoff;
ExaMigrationRec pixmaps[1];
int nbox = REGION_NUM_RECTS (pRegion);
BoxPtr pBox = REGION_RECTS (pRegion);
pixmaps[0].as_dst = TRUE;
pixmaps[0].as_src = FALSE;
@ -1031,15 +1029,43 @@ exaFillRegionSolid (DrawablePtr pDrawable,
if ((pPixmap = exaGetOffscreenPixmap (pDrawable, &xoff, &yoff)) &&
(*pExaScr->info->PrepareSolid) (pPixmap, alu, planemask, pixel))
{
int nbox;
BoxPtr pBox;
REGION_TRANSLATE(pScreen, pRegion, xoff, yoff);
nbox = REGION_NUM_RECTS (pRegion);
pBox = REGION_RECTS (pRegion);
while (nbox--)
{
(*pExaScr->info->Solid) (pPixmap,
pBox->x1 + xoff, pBox->y1 + yoff,
pBox->x2 + xoff, pBox->y2 + yoff);
(*pExaScr->info->Solid) (pPixmap, pBox->x1, pBox->y1, pBox->x2,
pBox->y2);
pBox++;
}
(*pExaScr->info->DoneSolid) (pPixmap);
exaMarkSync(pDrawable->pScreen);
if (pDrawable->width == 1 && pDrawable->height == 1 &&
pDrawable->bitsPerPixel != 24) {
ExaPixmapPriv(pPixmap);
switch (pDrawable->bitsPerPixel) {
case 32:
*(CARD32*)pExaPixmap->sys_ptr = pixel;
break;
case 16:
*(CARD16*)pExaPixmap->sys_ptr = pixel;
break;
case 8:
*(CARD8*)pExaPixmap->sys_ptr = pixel;
}
REGION_UNION(pScreen, &pExaPixmap->validSys, &pExaPixmap->validSys,
pRegion);
}
REGION_TRANSLATE(pScreen, pRegion, -xoff, -yoff);
}
else
{

View File

@ -358,16 +358,28 @@ exaGetPixmapFirstPixel (PixmapPtr pPixmap)
void *fb;
Bool need_finish = FALSE;
BoxRec box;
RegionRec migration;
ExaPixmapPriv (pPixmap);
Bool sys_valid = !miPointInRegion(&pExaPixmap->validSys, 0, 0, &box);
Bool damaged = miPointInRegion(DamageRegion(pExaPixmap->pDamage), 0, 0,
&box);
Bool offscreen = exaPixmapIsOffscreen(pPixmap);
fb = pExaPixmap->sys_ptr;
/* Try to avoid framebuffer readbacks */
if (exaPixmapIsOffscreen(pPixmap) &&
miPointInRegion(DamageRegion(pExaPixmap->pDamage), 0, 0, &box))
if ((!offscreen && !sys_valid && !damaged) ||
(offscreen && (!sys_valid || damaged)))
{
box.x1 = 0;
box.y1 = 0;
box.x2 = 1;
box.y2 = 1;
REGION_INIT(pScreen, &migration, &box, 1);
need_finish = TRUE;
exaPrepareAccess(&pPixmap->drawable, EXA_PREPARE_SRC);
exaPrepareAccessReg(&pPixmap->drawable, EXA_PREPARE_SRC, &migration);
fb = pPixmap->devPrivate.ptr;
}
@ -383,8 +395,10 @@ exaGetPixmapFirstPixel (PixmapPtr pPixmap)
break;
}
if (need_finish)
if (need_finish) {
exaFinishAccess(&pPixmap->drawable, EXA_PREPARE_SRC);
REGION_UNINIT(pScreen, &migration);
}
return pixel;
}