diff options
-rw-r--r-- | src/i830_dri.c | 152 |
1 files changed, 145 insertions, 7 deletions
diff --git a/src/i830_dri.c b/src/i830_dri.c index 6a324929..04154cc4 100644 --- a/src/i830_dri.c +++ b/src/i830_dri.c @@ -93,6 +93,12 @@ USE OR OTHER DEALINGS IN THE SOFTWARE. #ifdef DRI2 #include "dri2.h" + +#if DRI2INFOREC_VERSION >= 1 +#define USE_DRI2_1_1_0 +#endif + +extern XF86ModuleData dri2ModuleData; #endif static Bool I830InitVisualConfigs(ScreenPtr pScreen); @@ -1529,8 +1535,10 @@ I830DRIUnlock(ScrnInfoPtr pScrn) typedef struct { PixmapPtr pPixmap; + unsigned int attachment; } I830DRI2BufferPrivateRec, *I830DRI2BufferPrivatePtr; +#ifndef USE_DRI2_1_1_0 static DRI2BufferPtr I830DRI2CreateBuffers(DrawablePtr pDraw, unsigned int *attachments, int count) { @@ -1602,6 +1610,7 @@ I830DRI2CreateBuffers(DrawablePtr pDraw, unsigned int *attachments, int count) buffers[i].driverPrivate = &privates[i]; buffers[i].flags = 0; /* not tiled */ privates[i].pPixmap = pPixmap; + privates[i].attachment = attachments[i]; bo = i830_get_pixmap_bo (pPixmap); if (dri_bo_flink(bo, &buffers[i].name) != 0) { @@ -1613,6 +1622,88 @@ I830DRI2CreateBuffers(DrawablePtr pDraw, unsigned int *attachments, int count) return buffers; } +#else + +static DRI2BufferPtr +I830DRI2CreateBuffer(DrawablePtr pDraw, unsigned int attachment, + unsigned int format) +{ + ScreenPtr pScreen = pDraw->pScreen; + ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; + I830Ptr pI830 = I830PTR(pScrn); + DRI2BufferPtr buffers; + dri_bo *bo; + I830DRI2BufferPrivatePtr privates; + PixmapPtr pPixmap; + + buffers = xcalloc(1, sizeof *buffers); + if (buffers == NULL) + return NULL; + privates = xcalloc(1, sizeof *privates); + if (privates == NULL) { + xfree(buffers); + return NULL; + } + + if (attachment == DRI2BufferFrontLeft) { + if (pDraw->type == DRAWABLE_PIXMAP) + pPixmap = (PixmapPtr) pDraw; + else + pPixmap = (*pScreen->GetWindowPixmap)((WindowPtr) pDraw); + pPixmap->refcnt++; + } else { + unsigned int hint = 0; + + switch (attachment) { + case DRI2BufferDepth: + case DRI2BufferDepthStencil: + if (SUPPORTS_YTILING(pI830)) + hint = INTEL_CREATE_PIXMAP_TILING_Y; + else + hint = INTEL_CREATE_PIXMAP_TILING_X; + break; + case DRI2BufferFakeFrontLeft: + case DRI2BufferFakeFrontRight: + case DRI2BufferBackLeft: + case DRI2BufferBackRight: + hint = INTEL_CREATE_PIXMAP_TILING_X; + break; + } + + if (!pI830->tiling || + (!IS_I965G(pI830) && !pI830->kernel_exec_fencing)) + hint = 0; + + pPixmap = (*pScreen->CreatePixmap)(pScreen, + pDraw->width, + pDraw->height, + (format != 0)?format:pDraw->depth, + hint); + + } + + + buffers->attachment = attachment; + buffers->pitch = pPixmap->devKind; + buffers->cpp = pPixmap->drawable.bitsPerPixel / 8; + buffers->driverPrivate = privates; + buffers->format = format; + buffers->flags = 0; /* not tiled */ + privates->pPixmap = pPixmap; + privates->attachment = attachment; + + bo = i830_get_pixmap_bo (pPixmap); + if (dri_bo_flink(bo, &buffers->name) != 0) { + /* failed to name buffer */ + } + + return buffers; +} + +#endif + +#ifndef USE_DRI2_1_1_0 + static void I830DRI2DestroyBuffers(DrawablePtr pDraw, DRI2BufferPtr buffers, int count) { @@ -1633,15 +1724,37 @@ I830DRI2DestroyBuffers(DrawablePtr pDraw, DRI2BufferPtr buffers, int count) } } +#else + +static void +I830DRI2DestroyBuffer(DrawablePtr pDraw, DRI2BufferPtr buffer) +{ + if (buffer) { + I830DRI2BufferPrivatePtr private = buffer->driverPrivate; + ScreenPtr pScreen = pDraw->pScreen; + + (*pScreen->DestroyPixmap)(private->pPixmap); + + xfree(private); + xfree(buffer); + } +} + +#endif + static void I830DRI2CopyRegion(DrawablePtr pDraw, RegionPtr pRegion, - DRI2BufferPtr pDestBuffer, DRI2BufferPtr pSrcBuffer) + DRI2BufferPtr pDstBuffer, DRI2BufferPtr pSrcBuffer) { - I830DRI2BufferPrivatePtr private = pSrcBuffer->driverPrivate; + I830DRI2BufferPrivatePtr srcPrivate = pSrcBuffer->driverPrivate; + I830DRI2BufferPrivatePtr dstPrivate = pDstBuffer->driverPrivate; ScreenPtr pScreen = pDraw->pScreen; ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; I830Ptr pI830 = I830PTR(pScrn); - PixmapPtr pPixmap = private->pPixmap; + PixmapPtr pSrcPixmap = (srcPrivate->attachment == DRI2BufferFrontLeft) + ? (PixmapPtr) pDraw : srcPrivate->pPixmap; + PixmapPtr pDstPixmap = (dstPrivate->attachment == DRI2BufferFrontLeft) + ? (PixmapPtr) pDraw : dstPrivate->pPixmap; RegionPtr pCopyClip; GCPtr pGC; @@ -1649,9 +1762,9 @@ I830DRI2CopyRegion(DrawablePtr pDraw, RegionPtr pRegion, pCopyClip = REGION_CREATE(pScreen, NULL, 0); REGION_COPY(pScreen, pCopyClip, pRegion); (*pGC->funcs->ChangeClip) (pGC, CT_REGION, pCopyClip, 0); - ValidateGC(pDraw, pGC); - (*pGC->ops->CopyArea)(&pPixmap->drawable, - pDraw, pGC, 0, 0, pDraw->width, pDraw->height, 0, 0); + ValidateGC(&pDstPixmap->drawable, pGC); + (*pGC->ops->CopyArea)(&pSrcPixmap->drawable, &pDstPixmap->drawable, + pGC, 0, 0, pDraw->width, pDraw->height, 0, 0); FreeScratchGC(pGC); /* Emit a flush of the rendering cache, or on the 965 and beyond @@ -1680,12 +1793,28 @@ Bool I830DRI2ScreenInit(ScreenPtr pScreen) int i; struct stat sbuf; dev_t d; +#ifdef USE_DRI2_1_1_0 + int dri2_major = 1; + int dri2_minor = 0; +#endif if (pI830->accel != ACCEL_UXA) { xf86DrvMsg(pScrn->scrnIndex, X_WARNING, "DRI2 requires UXA\n"); return FALSE; } +#ifdef USE_DRI2_1_1_0 + if (xf86LoaderCheckSymbol("DRI2Version")) { + DRI2Version(& dri2_major, & dri2_minor); + } + + if (dri2_minor < 1) { + xf86DrvMsg(pScrn->scrnIndex, X_WARNING, + "DRI2 requires DRI2 module version 1.1.0 or later\n"); + return FALSE; + } +#endif + sprintf(buf, "pci:%04x:%02x:%02x.%d", pI830->PciInfo->domain, pI830->PciInfo->bus, @@ -1730,10 +1859,19 @@ Bool I830DRI2ScreenInit(ScreenPtr pScreen) info.driverName = IS_I965G(pI830) ? "i965" : "i915"; info.deviceName = p; - info.version = 1; +#ifdef USE_DRI2_1_1_0 + info.version = 2; + info.CreateBuffers = NULL; + info.DestroyBuffers = NULL; + info.CreateBuffer = I830DRI2CreateBuffer; + info.DestroyBuffer = I830DRI2DestroyBuffer; +#else + info.version = 1; info.CreateBuffers = I830DRI2CreateBuffers; info.DestroyBuffers = I830DRI2DestroyBuffers; +#endif + info.CopyRegion = I830DRI2CopyRegion; pI830->drmSubFD = info.fd; |