static void I810DRIInitBuffers(WindowPtr pWin, RegionPtr prgn, CARD32 index) { ScreenPtr pScreen = pWin->drawable.pScreen; ScrnInfoPtr pScrn = xf86ScreenToScrn(pScreen); BoxPtr pbox = REGION_RECTS(prgn); int nbox = REGION_NUM_RECTS(prgn); if (I810_DEBUG & DEBUG_VERBOSE_DRI) ErrorF("I810DRIInitBuffers\n"); I810SetupForSolidFill(pScrn, 0, GXcopy, -1); while (nbox--) { I810SelectBuffer(pScrn, I810_SELECT_BACK); I810SubsequentSolidFillRect(pScrn, pbox->x1, pbox->y1, pbox->x2 - pbox->x1, pbox->y2 - pbox->y1); pbox++; } /* Clear the depth buffer - uses 0xffff rather than 0. */ pbox = REGION_RECTS(prgn); nbox = REGION_NUM_RECTS(prgn); I810SelectBuffer(pScrn, I810_SELECT_DEPTH); I810SetupForSolidFill(pScrn, 0xffff, GXcopy, -1); while (nbox--) { I810SubsequentSolidFillRect(pScrn, pbox->x1, pbox->y1, pbox->x2 - pbox->x1, pbox->y2 - pbox->y1); pbox++; } I810SelectBuffer(pScrn, I810_SELECT_FRONT); I810DRISetNeedSync(pScrn); }
Bool I810DRIEnter(ScrnInfoPtr pScrn) { I810Ptr pI810 = I810PTR(pScrn); if (pI810->directRenderingEnabled) { if (pI810->agpAcquired == FALSE) drmAgpAcquire(pI810->drmSubFD); pI810->agpAcquired = TRUE; if (pI810->dcacheHandle != 0) if (drmAgpBind(pI810->drmSubFD, pI810->dcacheHandle, pI810->DepthOffset) != 0) return FALSE; if (pI810->backHandle != 0) if (drmAgpBind(pI810->drmSubFD, pI810->backHandle, pI810->BackOffset) != 0) return FALSE; if (pI810->zHandle != 0) if (drmAgpBind(pI810->drmSubFD, pI810->zHandle, pI810->DepthOffset) != 0) return FALSE; if (pI810->sysmemHandle != 0) if (drmAgpBind(pI810->drmSubFD, pI810->sysmemHandle, 0) != 0) return FALSE; if (pI810->xvmcHandle != 0) if (drmAgpBind(pI810->drmSubFD, pI810->xvmcHandle, pI810->MC.Start) != 0) return FALSE; if (pI810->cursorHandle != 0) if (drmAgpBind(pI810->drmSubFD, pI810->cursorHandle, pI810->CursorStart) != 0) return FALSE; if (pI810->cursorARGBHandle != 0) if (drmAgpBind(pI810->drmSubFD, pI810->cursorARGBHandle, pI810->CursorARGBStart) != 0) return FALSE; } I810SelectBuffer(pScrn, I810_SELECT_FRONT); return TRUE; }
/* This routine is a modified form of XAADoBitBlt with the calls to * ScreenToScreenBitBlt built in. My routine has the prgnSrc as source * instead of destination. My origin is upside down so the ydir cases * are reversed. * * KW: can you believe that this is called even when a 2d window moves? */ static void I810DRIMoveBuffers(WindowPtr pParent, DDXPointRec ptOldOrg, RegionPtr prgnSrc, CARD32 index) { ScreenPtr pScreen = pParent->drawable.pScreen; ScrnInfoPtr pScrn = xf86ScreenToScrn(pScreen); BoxPtr pboxTmp, pboxNext, pboxBase; DDXPointPtr pptTmp, pptNew2 = NULL; int xdir, ydir; int screenwidth = pScrn->virtualX; int screenheight = pScrn->virtualY; BoxPtr pbox = REGION_RECTS(prgnSrc); int nbox = REGION_NUM_RECTS(prgnSrc); BoxPtr pboxNew1 = NULL; BoxPtr pboxNew2 = NULL; DDXPointPtr pptNew1 = NULL; DDXPointPtr pptSrc = &ptOldOrg; int dx = pParent->drawable.x - ptOldOrg.x; int dy = pParent->drawable.y - ptOldOrg.y; /* If the copy will overlap in Y, reverse the order */ if (dy > 0) { ydir = -1; if (nbox > 1) { /* Keep ordering in each band, reverse order of bands */ pboxNew1 = (BoxPtr) malloc(sizeof(BoxRec) * nbox); if (!pboxNew1) return; pptNew1 = (DDXPointPtr) malloc(sizeof(DDXPointRec) * nbox); if (!pptNew1) { free(pboxNew1); return; } pboxBase = pboxNext = pbox + nbox - 1; while (pboxBase >= pbox) { while ((pboxNext >= pbox) && (pboxBase->y1 == pboxNext->y1)) pboxNext--; pboxTmp = pboxNext + 1; pptTmp = pptSrc + (pboxTmp - pbox); while (pboxTmp <= pboxBase) { *pboxNew1++ = *pboxTmp++; *pptNew1++ = *pptTmp++; } pboxBase = pboxNext; } pboxNew1 -= nbox; pbox = pboxNew1; pptNew1 -= nbox; pptSrc = pptNew1; } } else { /* No changes required */ ydir = 1; } /* If the regions will overlap in X, reverse the order */ if (dx > 0) { xdir = -1; if (nbox > 1) { /*reverse orderof rects in each band */ pboxNew2 = (BoxPtr) malloc(sizeof(BoxRec) * nbox); pptNew2 = (DDXPointPtr) malloc(sizeof(DDXPointRec) * nbox); if (!pboxNew2 || !pptNew2) { if (pptNew2) free(pptNew2); if (pboxNew2) free(pboxNew2); if (pboxNew1) { free(pptNew1); free(pboxNew1); } return; } pboxBase = pboxNext = pbox; while (pboxBase < pbox + nbox) { while ((pboxNext < pbox + nbox) && (pboxNext->y1 == pboxBase->y1)) pboxNext++; pboxTmp = pboxNext; pptTmp = pptSrc + (pboxTmp - pbox); while (pboxTmp != pboxBase) { *pboxNew2++ = *--pboxTmp; *pptNew2++ = *--pptTmp; } pboxBase = pboxNext; } pboxNew2 -= nbox; pbox = pboxNew2; pptNew2 -= nbox; pptSrc = pptNew2; } } else { /* No changes are needed */ xdir = 1; } /* SelectBuffer isn't really a good concept for the i810. */ I810EmitFlush(pScrn); I810SetupForScreenToScreenCopy(pScrn, xdir, ydir, GXcopy, -1, -1); for (; nbox--; pbox++) { int x1 = pbox->x1; int y1 = pbox->y1; int destx = x1 + dx; int desty = y1 + dy; int w = pbox->x2 - x1 + 1; int h = pbox->y2 - y1 + 1; if (destx < 0) x1 -= destx, w += destx, destx = 0; if (desty < 0) y1 -= desty, h += desty, desty = 0; if (destx + w > screenwidth) w = screenwidth - destx; if (desty + h > screenheight) h = screenheight - desty; if (w <= 0) continue; if (h <= 0) continue; if (I810_DEBUG & DEBUG_VERBOSE_DRI) ErrorF("MoveBuffers %d,%d %dx%d dx: %d dy: %d\n", x1, y1, w, h, dx, dy); I810SelectBuffer(pScrn, I810_SELECT_BACK); I810SubsequentScreenToScreenCopy(pScrn, x1, y1, destx, desty, w, h); I810SelectBuffer(pScrn, I810_SELECT_DEPTH); I810SubsequentScreenToScreenCopy(pScrn, x1, y1, destx, desty, w, h); } I810SelectBuffer(pScrn, I810_SELECT_FRONT); I810EmitFlush(pScrn); if (pboxNew2) { free(pptNew2); free(pboxNew2); } if (pboxNew1) { free(pptNew1); free(pboxNew1); } I810DRISetNeedSync(pScrn); }
/* The following function sets up the supported acceleration. Call it * from the FbInit() function in the SVGA driver, or before ScreenInit * in a monolithic server. */ Bool I810AccelInit(ScreenPtr pScreen) { XAAInfoRecPtr infoPtr; ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; I810Ptr pI810 = I810PTR(pScrn); if (I810_DEBUG & DEBUG_VERBOSE_ACCEL) ErrorF("I810AccelInit\n"); pI810->AccelInfoRec = infoPtr = XAACreateInfoRec(); if (!infoPtr) return FALSE; pI810->bufferOffset = 0; infoPtr->Flags = LINEAR_FRAMEBUFFER | OFFSCREEN_PIXMAPS; /* There is a bit blt bug in 24 bpp. This is a problem, but * at least without the pixmap cache we can pass the test suite */ if (pScrn->depth != 24) infoPtr->Flags |= PIXMAP_CACHE; /* Sync */ infoPtr->Sync = I810Sync; /* Solid filled rectangles */ { infoPtr->SolidFillFlags = NO_PLANEMASK; infoPtr->SetupForSolidFill = I810SetupForSolidFill; infoPtr->SubsequentSolidFillRect = I810SubsequentSolidFillRect; } /* Screen to screen copy * - the transparency op hangs the blit engine, disable for now. */ { infoPtr->ScreenToScreenCopyFlags = (0 | NO_PLANEMASK | NO_TRANSPARENCY | 0); infoPtr->SetupForScreenToScreenCopy = I810SetupForScreenToScreenCopy; infoPtr->SubsequentScreenToScreenCopy = I810SubsequentScreenToScreenCopy; } /* 8x8 pattern fills */ { infoPtr->SetupForMono8x8PatternFill = I810SetupForMono8x8PatternFill; infoPtr->SubsequentMono8x8PatternFillRect = I810SubsequentMono8x8PatternFillRect; infoPtr->Mono8x8PatternFillFlags = (HARDWARE_PATTERN_PROGRAMMED_BITS | HARDWARE_PATTERN_SCREEN_ORIGIN | BIT_ORDER_IN_BYTE_MSBFIRST | NO_PLANEMASK | 0); } /* 8x8 color fills - not considered useful for XAA. */ /* Scanline color expansion - Use the same scheme as the 3.3 driver. * */ if (pI810->Scratch.Size != 0) { int i; int width = ((pScrn->displayWidth + 31) & ~31) / 8; int nr_buffers = pI810->Scratch.Size / width; unsigned char *ptr = pI810->FbBase + pI810->Scratch.Start; pI810->NumScanlineColorExpandBuffers = nr_buffers; pI810->ScanlineColorExpandBuffers = (unsigned char **) xnfcalloc(nr_buffers, sizeof(unsigned char *)); for (i = 0; i < nr_buffers; i++, ptr += width) pI810->ScanlineColorExpandBuffers[i] = ptr; infoPtr->ScanlineCPUToScreenColorExpandFillFlags = (NO_PLANEMASK | ROP_NEEDS_SOURCE | BIT_ORDER_IN_BYTE_MSBFIRST | 0); infoPtr->ScanlineColorExpandBuffers = (unsigned char **) xnfcalloc(1, sizeof(unsigned char *)); infoPtr->NumScanlineColorExpandBuffers = 1; infoPtr->ScanlineColorExpandBuffers[0] = pI810->ScanlineColorExpandBuffers[0]; pI810->nextColorExpandBuf = 0; infoPtr->SetupForScanlineCPUToScreenColorExpandFill = I810SetupForScanlineCPUToScreenColorExpandFill; infoPtr->SubsequentScanlineCPUToScreenColorExpandFill = I810SubsequentScanlineCPUToScreenColorExpandFill; infoPtr->SubsequentColorExpandScanline = I810SubsequentColorExpandScanline; } /* Possible todo: Image writes w/ non-GXCOPY rop. */ I810SelectBuffer(pScrn, I810_SELECT_FRONT); return XAAInit(pScreen, infoPtr); }