diff options
author | Thomas Hellström <thomas@shipmail.org> | 2005-12-27 22:37:17 +0000 |
---|---|---|
committer | Thomas Hellström <thomas@shipmail.org> | 2005-12-27 22:37:17 +0000 |
commit | 45b1c58d70ecba76c0b978a2ab29c99c3e59ad29 (patch) | |
tree | 6897c017983e53ea9b6a2e517f5f4bc486e43cb1 | |
parent | 8207e3cc303c8e2797b184054f6b4dbe4471905e (diff) |
- Implement an experimental upload to screen using AGP texturing.
Works nicely on K8M800 but requires DRI to hand us AGP memory.
- Various temporary testing code implemented.
- Various 3D fixes. Probably broke AGP DMA (due to command alignments)
on the way.
-rw-r--r-- | ChangeLog | 18 | ||||
-rw-r--r-- | unichrome/via_accel.c | 499 | ||||
-rw-r--r-- | unichrome/via_driver.c | 2 | ||||
-rw-r--r-- | unichrome/via_driver.h | 17 |
4 files changed, 361 insertions, 175 deletions
@@ -1,3 +1,21 @@ +2005-12-27 Thomas Hellström <unichrome-at-shipmail-dot-org> + + * unichrome/via_accel.c: (viaExaPrepareCopy), + (viaExaCheckComposite), (viaExaPrepareComposite), + (viaExaComposite), (viaExaUploadToScreen), (viaInitExa), + (viaInitAccel), (viaOrder), (viaFinishInitAccel), + (viaSet3DDestination), (viaSet3DBlending), (viaSet3Dflags), + (viaSet3DDrawing), (viaSet3DTexture), (viaEmit3DState), + (viaEmitQuad), (test3d), (viaExaTexUploadToScreen): + * unichrome/via_driver.c: (VIAScreenInit): + * unichrome/via_driver.h: + + - Implement an experimental upload to screen using AGP texturing. + Works nicely on K8M800 but requires DRI to hand us AGP memory. + - Various temporary testing code implemented. + - Various 3D fixes. Probably broke AGP DMA (due to command alignments) + on the way. + 2005-12-16 Thomas Hellström <unichrome-at-shipmail-dot-org> * unichrome/via_accel.c: (viaFlushPCI), (viaFlushDRIEnabled), diff --git a/unichrome/via_accel.c b/unichrome/via_accel.c index e0acd78..df9364e 100644 --- a/unichrome/via_accel.c +++ b/unichrome/via_accel.c @@ -54,6 +54,9 @@ */ static void test3d(ScrnInfoPtr pScrn); +static Bool +viaExaTexUploadToScreen(PixmapPtr pDst, int x, int y, int w, int h, char *src, + int src_pitch); void viaFlushPCI(ViaCommandBuffer * buf) @@ -1228,7 +1231,7 @@ viaExaPrepareCopy(PixmapPtr pSrcPixmap, PixmapPtr pDstPixmap, int xdir, if (!viaAccelPlaneMaskHelper(tdc, planeMask)) return FALSE; viaAccelTransparentHelper(tdc, cb, 0x0, 0x0, TRUE); - test3d(pScrn); + /* test3d(pScrn); */ return TRUE; } @@ -1254,6 +1257,27 @@ viaExaCopy(PixmapPtr pDstPixmap, int srcX, int srcY, int dstX, int dstY, ADVANCE_RING; } +static Bool +viaExaCheckComposite(int op, PicturePtr pSrcPicture, + PicturePtr pMaskPicture, PicturePtr pDstPicture) +{ + return FALSE; +} + +static Bool +viaExaPrepareComposite(int op, PicturePtr pSrcPicture, + PicturePtr pMaskPicture, PicturePtr pDstPicture, + PixmapPtr pSrc, PixmapPtr pMask, PixmapPtr pDst) +{ + return FALSE; +} + +static void +viaExaComposite(PixmapPtr pDst, int srcX, int srcY, int maskX, int maskY, + int dstX, int dstY, int width, int height) +{ +} + #ifdef XF86DRI /* @@ -1347,7 +1371,10 @@ viaExaUploadToScreen(PixmapPtr pDst, int x, int y, int w, int h, char *src, if (!pVia->directRenderingEnabled) return FALSE; - +#if 1 + if (viaExaTexUploadToScreen(pDst, x, y, w, h, src, src_pitch)) + return TRUE; +#endif if (((unsigned long)src & 15) || (src_pitch & 15)) return FALSE; @@ -1376,6 +1403,7 @@ viaExaUploadToScreen(PixmapPtr pDst, int x, int y, int w, int h, char *src, &blit.sync, sizeof(blit.sync)))) ; return (err == 0); } + #endif /* @@ -1420,9 +1448,9 @@ viaInitExa(ScreenPtr pScreen) } #endif - /* - * Composite not supported. Could we use the 3D engine? - */ + pExa->accel.CheckComposite = viaExaCheckComposite; + pExa->accel.PrepareComposite = viaExaPrepareComposite; + pExa->accel.Composite = viaExaComposite; if (!exaDriverInit(pScreen, pExa)) { xfree(pExa); @@ -1474,7 +1502,7 @@ viaInitAccel(ScreenPtr pScreen) pVia->FBFreeEnd -= 32; pVia->markerOffset = (pVia->FBFreeEnd + 31) & ~31; pVia->markerBuf = (CARD32 *) ((char *)pVia->FBBase + pVia->markerOffset); - pVia->FBFreeEnd -= 1024 * 1024; + pVia->FBFreeEnd -= 1024 * 1024 * 4; pVia->testOffset = (pVia->FBFreeEnd + 31) & ~31; pVia->testBuf = (char *)pVia->FBBase + pVia->testOffset; @@ -1507,7 +1535,7 @@ viaInitAccel(ScreenPtr pScreen) /* * Memory distribution for XAA is tricky. We'd like to make the * pixmap cache no larger than 3 x visible screen size, otherwise - * XAA may get slow for some reason. + * XAA may get slow for some undetermined reason. */ #ifdef XF86DRI @@ -1567,6 +1595,49 @@ viaExitAccel(ScreenPtr pScreen) } } +static Bool +viaOrder(CARD32 val, CARD32 * shift) +{ + *shift = 0; + + while (val > (1 << *shift)) + (*shift)++; + return (val == (1 << *shift)); +} + +void +viaFinishInitAccel(ScreenPtr pScreen) +{ +#ifdef XF86DRI + ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum]; + VIAPtr pVia = VIAPTR(pScrn); + int order, size, ret; + + pVia->texAddr = NULL; + if (pVia->directRenderingEnabled) { + if (!pVia->IsPCI) { + viaOrder(pScrn->displayWidth * pVia->Bpp, &order); + size = (1 << order) * pScrn->virtualY + 32; + pVia->texAGPBuffer.context = 1; + pVia->texAGPBuffer.size = size; + pVia->texAGPBuffer.type = VIA_MEM_AGP; + ret = + drmCommandWriteRead(pVia->drmFD, DRM_VIA_ALLOCMEM, + &pVia->texAGPBuffer, sizeof(drm_via_mem_t)); + if (ret || size != pVia->texAGPBuffer.size) { + pVia->texAGPBuffer.size = 0; + } else { + xf86DrvMsg(pScrn->scrnIndex, X_INFO, + "Allocated %u kiB of AGP memory for system to frame-buffer transfer.\n", + size / 1024); + pVia->texOffset = (pVia->texAGPBuffer.offset + 31) & ~31; + pVia->texAddr = (char *)pVia->agpMappedAddr + pVia->texOffset; + } + } + } +#endif +} + /* * DGA accelerated functions go here and let them be independent of acceleration * method. @@ -1640,37 +1711,50 @@ viaDGAWaitMarker(ScrnInfoPtr pScrn) static void viaSet3DDestination(ScrnInfoPtr pScrn, Via3DState * v3d, CARD32 offset, - CARD32 pitch, ViaImageFormats format, Bool alphaBuffer, - CARD32 alphaOffset, CARD32 alphaPitch, ViaImageFormats alphaFormat) + CARD32 pitch, ViaImageFormats format) { + v3d->drawingDirty = TRUE; /* Affects planemask format. */ + v3d->destDirty = TRUE; v3d->destOffset = offset; v3d->destPitch = pitch; - v3d->destFormat = format; - v3d->alphaBuffer = alphaBuffer; - v3d->alphaOffset = alphaOffset; - v3d->alphaPitch = alphaPitch; - - /* - * Alpha buffer formats are undocumented. - * We assume alpha buffer formats are the same as the ones used - * for alpha textures. - */ - - v3d->alphaFormat = alphaFormat - via_a1; + switch (format) { + case via_argb8888: + v3d->destFormat = HC_HDBFM_ARGB8888; + v3d->destDepth = 32; + break; + case via_rgb888: + v3d->destFormat = HC_HDBFM_ARGB0888; + v3d->destDepth = 32; + break; + case via_rgb565: + default: + v3d->destFormat = HC_HDBFM_RGB565; + v3d->destDepth = 16; + break; + } } +/* + * Set blending mode. + * 0 - No blending. + * 1 - C_out = src_alpha * C_src + (1. - src_alpha) * C_dst + * 2 - C_out = dst_alpha * C_src + (1. - dst_alpha) * C_dst + * 3 - C_out = C_src * C_dst, alpha_out = src_alpha * dst_alpha + */ + static void -viaSet3DBlending(ScrnInfoPtr pScrn, Via3DState * v3d, Bool blend, +viaSet3DBlending(ScrnInfoPtr pScrn, Via3DState * v3d, int blend, Bool useDestAlpha) { + v3d->blendDirty = TRUE; v3d->blend = blend; - v3d->useDestAlpha = useDestAlpha; } static void viaSet3Dflags(ScrnInfoPtr pScrn, Via3DState * v3d, int numTextures, Bool writeAlpha, Bool writeColor) { + v3d->enableDirty = TRUE; v3d->numTextures = numTextures; v3d->writeAlpha = writeAlpha; v3d->writeColor = writeColor; @@ -1680,6 +1764,7 @@ static void viaSet3DDrawing(ScrnInfoPtr pScrn, Via3DState * v3d, int rop, CARD32 planeMask, CARD32 solidColor, CARD32 solidAlpha) { + v3d->drawingDirty = TRUE; v3d->rop = rop; v3d->planeMask = planeMask; v3d->solidColor = solidColor; @@ -1687,16 +1772,6 @@ viaSet3DDrawing(ScrnInfoPtr pScrn, Via3DState * v3d, int rop, } static Bool -viaOrder(CARD32 val, CARD32 * shift) -{ - *shift = 0; - - while (val > (1 << *shift)) - (*shift)++; - return (val == (1 << *shift)); -} - -static Bool viaSet3DTexture(ScrnInfoPtr pScrn, Via3DState * v3d, int tex, CARD32 offset, CARD32 pitch, CARD32 width, CARD32 height, ViaImageFormats format, ViaTextureModes sMode, ViaTextureModes tMode, Bool textureCol, @@ -1712,12 +1787,16 @@ viaSet3DTexture(ScrnInfoPtr pScrn, Via3DState * v3d, int tex, CARD32 offset, return FALSE; switch (format) { + case via_rgb565: + v3d->textureFormat[tex] = HC_HTXnFM_RGB565; + break; default: v3d->textureFormat[tex] = HC_HTXnFM_ARGB8888; } - v3d->textureModesS[tex] = sMode - via_repeat; - v3d->textureModesT[tex] = tMode - via_repeat; + v3d->textureDirty[tex] = TRUE; + v3d->textureModesS[tex] = sMode - via_single; + v3d->textureModesT[tex] = tMode - via_single; v3d->textureCol[tex] = textureCol; v3d->textureAlpha[tex] = textureAlpha; @@ -1741,141 +1820,165 @@ static void viaEmit3DState(ScrnInfoPtr pScrn, Via3DState * v3d) { VIAPtr pVia = VIAPTR(pScrn); - CARD32 format, planeMaskLo, planeMaskHi; int i; + Bool forceUpload; - RING_VARS; + forceUpload = (pVia->lastToUpload != v3d); + pVia->lastToUpload = v3d; - BEGIN_H2(HC_ParaType_NotTex, 13); +#ifdef XF86DRI /* - * Destination buffer location, format and pitch. + * Tell DRI clients that we have uploaded a 3D state to the engine. */ - OUT_RING_SubA(HC_SubA_HDBBasL, v3d->destOffset & 0x00FFFFFF); - OUT_RING_SubA(HC_SubA_HDBBasH, v3d->destOffset >> 24); - switch (v3d->destFormat) { - case via_rgb888: - format = HC_HDBFM_ARGB0888; - planeMaskLo = v3d->planeMask & 0x00FFFFFF; - planeMaskHi = v3d->planeMask >> 24; - break; - case via_rgb565: - default: - format = HC_HDBFM_RGB565; - planeMaskLo = (v3d->planeMask & 0x000000FF) << 16; - planeMaskHi = (v3d->planeMask & 0x0000FF00) >> 8; - break; - } - OUT_RING_SubA(HC_SubA_HDBFM, format | - (v3d->destPitch & HC_HDBPit_MASK) | HC_HDBLoc_Local); - - /* - * The Alpha-buffer is undocumented, but with some hints in the 3D header file. - */ + if (pVia->directRenderingEnabled) { + volatile drm_via_sarea_t *saPriv = (drm_via_sarea_t *) + DRIGetSAREAPrivate(pScrn->pScreen); + int myContext = DRIGetContext(pScrn->pScreen); - if (v3d->alphaBuffer) { - OUT_RING_SubA(HC_SubA_HABBasL, v3d->alphaOffset & 0x00FFFFFF); - OUT_RING_SubA(HC_SubA_HABBasH, v3d->alphaOffset >> 24); - OUT_RING_SubA(HC_SubA_HABFM, (v3d->alphaFormat << 16) | - (v3d->alphaPitch & HC_HABPit_MASK) | HC_HDBLoc_Local); + forceUpload = forceUpload || (saPriv->ctxOwner != myContext); + saPriv->ctxOwner = myContext; } +#endif + + RING_VARS; /* - * Blending. Set up the blending equation - * Dst_C = alpha * Source_C + (1 - alpha)*Dst_C - * alpha is read either from source or from destination. + * Destination buffer location, format and pitch. */ - if (v3d->blend) { - OUT_RING_SubA(HC_SubA_HABLCsat, (0x01 << 16) | (0x00 << 10) | - (((v3d->useDestAlpha) ? 0x03 : 0x02) << 4)); - OUT_RING_SubA(HC_SubA_HABLCop, (0x00 << 14) | (0x01 << 8) | - (((v3d->useDestAlpha) ? 0x13 : 0x12) << 2)); + if (forceUpload || v3d->destDirty) { + v3d->destDirty = FALSE; + BEGIN_H2(HC_ParaType_NotTex, 3); + + OUT_RING_SubA(HC_SubA_HDBBasL, v3d->destOffset & 0x00FFFFFF); + OUT_RING_SubA(HC_SubA_HDBBasH, v3d->destOffset >> 24); + OUT_RING_SubA(HC_SubA_HDBFM, v3d->destFormat | + (v3d->destPitch & HC_HDBPit_MASK) | HC_HDBLoc_Local); } - /* - * Raster operation and Planemask. - */ + if (forceUpload || v3d->blendDirty) { + v3d->blendDirty = FALSE; + BEGIN_H2(HC_ParaType_NotTex, 6); + + if (v3d->blend) { + switch (v3d->blend) { + case 1: + case 2: + OUT_RING_SubA(HC_SubA_HABLCsat, (0x01 << 16) | (0x00 << 10) | + (((v3d->blend == 2) ? 0x03 : 0x02) << 4)); + OUT_RING_SubA(HC_SubA_HABLCop, (0x00 << 14) | (0x01 << 8) | + (((v3d->blend == 2) ? 0x13 : 0x12) << 2)); + break; + case 3: + OUT_RING_SubA(HC_SubA_HABLCsat, (0x00 << 16) | (0x00 << 10) | + (0x01 << 4)); + OUT_RING_SubA(HC_SubA_HABLCop, (0x05 << 8) | (0x05 << 2)); + OUT_RING_SubA(HC_SubA_HABLRCb, 0x00); + OUT_RING_SubA(HC_SubA_HABLRFCb, 0x00); + OUT_RING_SubA(HC_SubA_HABLAsat, (0x00 << 16) | (0x01 << 10) | + (0x02 << 4)); + OUT_RING_SubA(HC_SubA_HABLAop, 0x00); + + break; + default: + break; + } + } + } - OUT_RING_SubA(HC_SubA_HROP, ((v3d->rop & 0x0F) << 8) | planeMaskHi); - OUT_RING_SubA(HC_SubA_HFBBMSKL, planeMaskLo); + if (forceUpload || v3d->drawingDirty) { - /* - * Solid shading color and alpha. Pixel center at - * floating coordinates (X.5,Y.5). - */ + CARD32 planeMaskLo, planeMaskHi; - OUT_RING_SubA(HC_SubA_HSolidCL, v3d->solidColor & 0x00FFFFFF); - OUT_RING_SubA(HC_SubA_HPixGC, - ((v3d->solidColor & 0xFF000000) >> 16) | (0 << 23) | (v3d-> - solidAlpha & 0xFF)); + v3d->drawingDirty = FALSE; + BEGIN_H2(HC_ParaType_NotTex, 4); - /* - * Enable setting - */ + /* + * Raster operation and Planemask. + */ - OUT_RING_SubA(HC_SubA_HEnable, ((v3d->writeColor) ? HC_HenCW_MASK : 0) | - ((v3d->blend) ? HC_HenABL_MASK : 0) | - ((v3d->numTextures) ? HC_HenTXMP_MASK : 0) | - ((v3d->writeAlpha) ? HC_HenAW_MASK : 0)); + if (/* v3d->destDepth == 16 Bad Docs? */ FALSE ) { + planeMaskLo = (v3d->planeMask & 0x000000FF) << 16; + planeMaskHi = (v3d->planeMask & 0x0000FF00) >> 8; + } else { + planeMaskLo = v3d->planeMask & 0x00FFFFFF; + planeMaskHi = v3d->planeMask >> 24; + } - /* - * Textures - */ + OUT_RING_SubA(HC_SubA_HROP, ((v3d->rop & 0x0F) << 8) | planeMaskHi); + OUT_RING_SubA(HC_SubA_HFBBMSKL, planeMaskLo); - if (v3d->numTextures) { - BEGIN_H2((HC_ParaType_Tex | (HC_SubType_TexGeneral << 8)), 1); - OUT_RING_SubA(HC_SubA_HTXSMD, (0 << 7) | (0 << 6) | - (((v3d->numTextures - 1) & 0x1) << 3) | (0 << 1) | 1); - OUT_RING_SubA(HC_SubA_HTXSMD, (0 << 7) | (0 << 6) | - (((v3d->numTextures - 1) & 0x1) << 3) | (0 << 1) | 0); - } + /* + * Solid shading color and alpha. Pixel center at + * floating coordinates (X.5,Y.5). + */ - for (i = 0; i < v3d->numTextures; ++i) { - BEGIN_H2((HC_ParaType_Tex | - (((i == 0) ? HC_SubType_Tex0 : HC_SubType_Tex1) << 8)), 13); - - OUT_RING_SubA(HC_SubA_HTXnFM, (v3d->textureFormat[i] | - (v3d->agpTexture[i] ? HC_HTXnLoc_AGP : HC_HTXnLoc_Local))); - OUT_RING_SubA(HC_SubA_HTXnL0BasL, - v3d->textureLevel0Offset[i] & 0x00FFFFFF); - OUT_RING_SubA(HC_SubA_HTXnL012BasH, - v3d->textureLevel0Offset[i] >> 24); - OUT_RING_SubA(HC_SubA_HTXnL0Pit, v3d->textureLevel0Exp[i] << 20); - OUT_RING_SubA(HC_SubA_HTXnL0_5WE, v3d->textureLevel0WExp[i]); - OUT_RING_SubA(HC_SubA_HTXnL0_5HE, v3d->textureLevel0HExp[i]); - OUT_RING_SubA(HC_SubA_HTXnL0OS, 0x00); - OUT_RING_SubA(HC_SubA_HTXnTB, 0x00); - OUT_RING_SubA(HC_SubA_HTXnMPMD, - (((unsigned)v3d->textureModesT[i]) << 19) | (((unsigned)v3d-> - textureModesS[i]) << 16)); - - OUT_RING_SubA(HC_SubA_HTXnTBLCsat, 0x00); - OUT_RING_SubA(HC_SubA_HTXnTBLCop, - ((v3d->textureCol[i] ? 3 : 4) << 14) | (2 << 11) | ((v3d-> - textureAlpha[i] ? 4 : 2) << 3) | 2); - - OUT_RING_SubA(HC_SubA_HTXnTBLAsat, (3 << 14) | (3 << 7) | 3); - OUT_RING_SubA(HC_SubA_HTXnTBLRAa, 0x00); + OUT_RING_SubA(HC_SubA_HSolidCL, + (v3d->solidColor & 0x00FFFFFF) | (0 << 23)); + OUT_RING_SubA(HC_SubA_HPixGC, + ((v3d->solidColor & 0xFF000000) >> 16) | (0 << 23) | (v3d-> + solidAlpha & 0xFF)); } - ADVANCE_RING; - -#ifdef XF86DRI - - /* - * Tell DRI clients that we have uploaded a 3D state to the engine. - */ + if (forceUpload || v3d->enableDirty) { + v3d->enableDirty = FALSE; + BEGIN_H2(HC_ParaType_NotTex, 1); - if (pVia->directRenderingEnabled) { - volatile drm_via_sarea_t *saPriv = (drm_via_sarea_t *) - DRIGetSAREAPrivate(pScrn->pScreen); + /* + * Enable setting + */ + OUT_RING_SubA(HC_SubA_HEnable, + ((v3d->writeColor) ? HC_HenCW_MASK : 0) | ((v3d-> + blend) ? HC_HenABL_MASK : 0) | ((v3d-> + numTextures) ? HC_HenTXMP_MASK : 0) | ((v3d-> + writeAlpha) ? HC_HenAW_MASK : 0)); + + if (v3d->numTextures) { + BEGIN_H2((HC_ParaType_Tex | (HC_SubType_TexGeneral << 8)), 2); + OUT_RING_SubA(HC_SubA_HTXSMD, (0 << 7) | (0 << 6) | + (((v3d->numTextures - 1) & 0x1) << 3) | (0 << 1) | 1); + OUT_RING_SubA(HC_SubA_HTXSMD, (0 << 7) | (0 << 6) | + (((v3d->numTextures - 1) & 0x1) << 3) | (0 << 1) | 0); + } + } - saPriv->ctxOwner = DRIGetContext(pScrn->pScreen); + for (i = 0; i < v3d->numTextures; ++i) { + if (forceUpload || v3d->textureDirty[i]) { + v3d->textureDirty[i] = FALSE; + + BEGIN_H2((HC_ParaType_Tex | + (((i == 0) ? HC_SubType_Tex0 : HC_SubType_Tex1) << 8)), + 13); + + OUT_RING_SubA(HC_SubA_HTXnFM, (v3d->textureFormat[i] | + (v3d-> + agpTexture[i] ? HC_HTXnLoc_AGP : HC_HTXnLoc_Local))); + OUT_RING_SubA(HC_SubA_HTXnL0BasL, + v3d->textureLevel0Offset[i] & 0x00FFFFFF); + OUT_RING_SubA(HC_SubA_HTXnL012BasH, + v3d->textureLevel0Offset[i] >> 24); + OUT_RING_SubA(HC_SubA_HTXnL0Pit, v3d->textureLevel0Exp[i] << 20); + OUT_RING_SubA(HC_SubA_HTXnL0_5WE, v3d->textureLevel0WExp[i]); + OUT_RING_SubA(HC_SubA_HTXnL0_5HE, v3d->textureLevel0HExp[i]); + OUT_RING_SubA(HC_SubA_HTXnL0OS, 0x00); + OUT_RING_SubA(HC_SubA_HTXnTB, 0x00); + OUT_RING_SubA(HC_SubA_HTXnMPMD, + (((unsigned)v3d->textureModesT[i]) << 19) | (((unsigned)v3d-> + textureModesS[i]) << 16)); + + OUT_RING_SubA(HC_SubA_HTXnTBLCsat, 0x00); + OUT_RING_SubA(HC_SubA_HTXnTBLCop, + ((v3d->textureCol[i] ? 3 : 4) << 14) | (2 << 11) | ((v3d-> + textureAlpha[i] ? 4 : 2) << 3) | 2); + + OUT_RING_SubA(HC_SubA_HTXnTBLAsat, (3 << 14) | (3 << 7) | 3); + OUT_RING_SubA(HC_SubA_HTXnTBLRAa, 0x00); + } } -#endif + ADVANCE_RING; } static void @@ -1884,8 +1987,8 @@ viaEmitQuad(ScrnInfoPtr pScrn, Via3DState * v3d, int dstX, int dstY, { VIAPtr pVia = VIAPTR(pScrn); CARD32 acmd; - float dx1, dx2, dy1, dy2, sx1[2], sx2[2], sy1[2], sy2[2], z; - float scalex, scaley; + float dx1, dx2, dy1, dy2, sx1[2], sx2[2], sy1[2], sy2[2], wf; + double scalex, scaley; int i, numTex; RING_VARS; @@ -1902,8 +2005,8 @@ viaEmitQuad(ScrnInfoPtr pScrn, Via3DState * v3d, int dstX, int dstY, sy1[0] = src0Y; sy1[1] = src1Y; for (i = 0; i < numTex; ++i) { - scalex = 1. / (float)(1 << v3d->textureLevel0WExp[i]); - scaley = 1. / (float)(1 << v3d->textureLevel0HExp[i]); + scalex = 1. / (double)((1 << v3d->textureLevel0WExp[i])); + scaley = 1. / (double)((1 << v3d->textureLevel0HExp[i])); sx2[i] = sx1[i] + w; sy2[i] = sy1[i] + h; sx1[i] *= scalex; @@ -1913,23 +2016,25 @@ viaEmitQuad(ScrnInfoPtr pScrn, Via3DState * v3d, int dstX, int dstY, } } - z = 0.; + wf = 0.05; /* * Cliprect */ BEGIN_H2(HC_ParaType_NotTex, 4); - OUT_RING_SubA(HC_SubA_HClipTB, (dstY << 12) | (dstY + h - 1)); - OUT_RING_SubA(HC_SubA_HClipLR, (dstX << 12) | (dstX + w - 1)); + OUT_RING_SubA(HC_SubA_HClipTB, (dstY << 12) | (dstY + h)); + OUT_RING_SubA(HC_SubA_HClipLR, (dstX << 12) | (dstX + w)); /* - * Vertex buffer. Emit two 3-point triangles. The Z coordinate - * is needed for AGP DMA, but is never used. + * Vertex buffer. Emit two 3-point triangles. The W or Z coordinate + * is needed for AGP DMA, and the W coordinate is for some obscure + * reason needed for texture mapping to be done correctly. So emit + * a w value after the x and y coordinates. */ BEGIN_H2(HC_ParaType_CmdVdata, 22 + numTex * 6); - acmd = ((1 << 14) | (1 << 13) | (1 << 12)); + acmd = ((1 << 14) | (1 << 13) | (1 << 11)); if (numTex) acmd |= ((1 << 7) | (1 << 8)); OUT_RING_SubA(0xEC, acmd); @@ -1939,7 +2044,7 @@ viaEmitQuad(ScrnInfoPtr pScrn, Via3DState * v3d, int dstX, int dstY, OUT_RING(*((CARD32 *) (&dx1))); OUT_RING(*((CARD32 *) (&dy1))); - OUT_RING(*((CARD32 *) (&z))); + OUT_RING(*((CARD32 *) (&wf))); for (i = 0; i < numTex; ++i) { OUT_RING(*((CARD32 *) (sx1 + i))); OUT_RING(*((CARD32 *) (sy1 + i))); @@ -1947,7 +2052,7 @@ viaEmitQuad(ScrnInfoPtr pScrn, Via3DState * v3d, int dstX, int dstY, OUT_RING(*((CARD32 *) (&dx2))); OUT_RING(*((CARD32 *) (&dy1))); - OUT_RING(*((CARD32 *) (&z))); + OUT_RING(*((CARD32 *) (&wf))); for (i = 0; i < numTex; ++i) { OUT_RING(*((CARD32 *) (sx2 + i))); OUT_RING(*((CARD32 *) (sy1 + i))); @@ -1955,7 +2060,7 @@ viaEmitQuad(ScrnInfoPtr pScrn, Via3DState * v3d, int dstX, int dstY, OUT_RING(*((CARD32 *) (&dx1))); OUT_RING(*((CARD32 *) (&dy2))); - OUT_RING(*((CARD32 *) (&z))); + OUT_RING(*((CARD32 *) (&wf))); for (i = 0; i < numTex; ++i) { OUT_RING(*((CARD32 *) (sx1 + i))); OUT_RING(*((CARD32 *) (sy2 + i))); @@ -1963,7 +2068,7 @@ viaEmitQuad(ScrnInfoPtr pScrn, Via3DState * v3d, int dstX, int dstY, OUT_RING(*((CARD32 *) (&dx1))); OUT_RING(*((CARD32 *) (&dy2))); - OUT_RING(*((CARD32 *) (&z))); + OUT_RING(*((CARD32 *) (&wf))); for (i = 0; i < numTex; ++i) { OUT_RING(*((CARD32 *) (sx1 + i))); OUT_RING(*((CARD32 *) (sy2 + i))); @@ -1971,7 +2076,7 @@ viaEmitQuad(ScrnInfoPtr pScrn, Via3DState * v3d, int dstX, int dstY, OUT_RING(*((CARD32 *) (&dx2))); OUT_RING(*((CARD32 *) (&dy1))); - OUT_RING(*((CARD32 *) (&z))); + OUT_RING(*((CARD32 *) (&wf))); for (i = 0; i < numTex; ++i) { OUT_RING(*((CARD32 *) (sx2 + i))); OUT_RING(*((CARD32 *) (sy1 + i))); @@ -1979,16 +2084,14 @@ viaEmitQuad(ScrnInfoPtr pScrn, Via3DState * v3d, int dstX, int dstY, OUT_RING(*((CARD32 *) (&dx2))); OUT_RING(*((CARD32 *) (&dy2))); - OUT_RING(*((CARD32 *) (&z))); + OUT_RING(*((CARD32 *) (&wf))); for (i = 0; i < numTex; ++i) { OUT_RING(*((CARD32 *) (sx2 + i))); OUT_RING(*((CARD32 *) (sy2 + i))); } - - OUT_RING_SubA(0xEE, - acmd | HC_HPLEND_MASK | HC_HPMValidN_MASK | HC_HE3Fire_MASK); OUT_RING_SubA(0xEE, acmd | HC_HPLEND_MASK | HC_HPMValidN_MASK | HC_HE3Fire_MASK); + OUT_RING(0x00000000); ADVANCE_RING; } @@ -2003,24 +2106,80 @@ test3d(ScrnInfoPtr pScrn) if (!done) { done = TRUE; - for (j = 0; j < 256; ++j) { - for (i = 0; i < 256; ++i) { - *((CARD32 *) (pVia->testBuf + (i * 4 + j * 1024))) = - i | (j << 24); + for (j = 0; j < 512; ++j) { + for (i = 0; i < 512; i += 2) { + *((CARD32 *) (pVia->testBuf + (i * 4 + j * 2048))) = + 0x00FF0000; + *((CARD32 *) (pVia->testBuf + ((i + 1) * 4 + j * 2048))) = + 0x000000FF; } } } - viaSet3DDestination(pScrn, v3d, 0x00000000, pVia->Bpl, via_rgb888, - FALSE, 0x00000000, 0x00000000, via_a8); - viaSet3DBlending(pScrn, v3d, TRUE, FALSE); + viaSet3DDestination(pScrn, v3d, 0x00000000, pVia->Bpl, via_rgb888); + viaSet3DBlending(pScrn, v3d, FALSE, FALSE); viaSet3DDrawing(pScrn, v3d, 0x0c, 0xFFFFFFFF, 0x000000FF, 0x00); viaSet3Dflags(pScrn, v3d, 1, FALSE, TRUE); - if (!viaSet3DTexture(pScrn, v3d, 0, pVia->testOffset, 1024, - 256, 256, via_argb8888, via_repeat, via_repeat, TRUE, TRUE, + if (!viaSet3DTexture(pScrn, v3d, 0, pVia->testOffset, 2048, + 512, 512, via_argb8888, via_repeat, via_repeat, TRUE, TRUE, FALSE)) { ErrorF("Texture Error\n"); return; } viaEmit3DState(pScrn, v3d); - viaEmitQuad(pScrn, v3d, 800, 800, 0, 0, 0, 0, 200, 100); + viaEmitQuad(pScrn, v3d, 600, 600, 0, 0, 0, 0, 512, 512); + viaAccelSync(pScrn); +} + +static Bool +viaExaTexUploadToScreen(PixmapPtr pDst, int x, int y, int w, int h, char *src, + int src_pitch) +{ + ScrnInfoPtr pScrn = xf86Screens[pDst->drawable.pScreen->myNum]; + VIAPtr pVia = VIAPTR(pScrn); + unsigned dstPitch = exaGetPixmapPitch(pDst); + unsigned bytesPerPixel = pDst->drawable.bitsPerPixel >> 3; + unsigned dstOffset = exaGetPixmapOffset(pDst); + unsigned texWidth, texHeight, texPitch; + ViaImageFormats format; + int i; + + if (!pVia->texAddr) + return FALSE; + + switch (bytesPerPixel) { + case 4: + format = via_argb8888; + break; + case 2: + format = via_rgb565; + break; + default: + return FALSE; + } + + viaOrder(w * bytesPerPixel, &texPitch); + texPitch = 1 << texPitch; + viaOrder(w, &texWidth); + texWidth = 1 << texWidth; + viaOrder(h, &texHeight); + texHeight = 1 << texHeight; + + viaSet3DDestination(pScrn, &pVia->v3d, dstOffset, dstPitch, format); + viaSet3DBlending(pScrn, &pVia->v3d, FALSE, FALSE); + viaSet3DDrawing(pScrn, &pVia->v3d, 0x0c, 0xFFFFFFFF, 0x000000FF, 0x00); + viaSet3Dflags(pScrn, &pVia->v3d, 1, TRUE, TRUE); + if (!viaSet3DTexture(pScrn, &pVia->v3d, 0, pVia->texOffset, texPitch, + texWidth, texHeight, format, via_single, via_single, TRUE, TRUE, + TRUE)) + return FALSE; + viaEmit3DState(pScrn, &pVia->v3d); + + for (i = 0; i < h; ++i) { + memcpy(pVia->texAddr + i * texPitch, src + i * src_pitch, + w * bytesPerPixel); + } + viaEmitQuad(pScrn, &pVia->v3d, x, y, 0, 0, 0, 0, w, h); + viaAccelSync(pScrn); + + return TRUE; } diff --git a/unichrome/via_driver.c b/unichrome/via_driver.c index fc632ec..b2fe0e5 100644 --- a/unichrome/via_driver.c +++ b/unichrome/via_driver.c @@ -2207,6 +2207,8 @@ VIAScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv) xf86DrvMsg(pScrn->scrnIndex, X_INFO, "direct rendering disabled\n"); } #endif + if (!pVia->NoAccel) + viaFinishInitAccel(pScreen); viaInitVideo(pScreen); diff --git a/unichrome/via_driver.h b/unichrome/via_driver.h index 2c0f6d2..c806020 100644 --- a/unichrome/via_driver.h +++ b/unichrome/via_driver.h @@ -186,17 +186,18 @@ typedef enum{ #define VIA_NUM_TEXUNITS 2 typedef struct _Via3DState{ + Bool destDirty; + Bool blendDirty; + Bool enableDirty; + Bool drawingDirty; CARD32 rop; CARD32 planeMask; CARD32 solidColor; CARD32 solidAlpha; CARD32 destOffset; CARD32 destPitch; - ViaImageFormats destFormat; - Bool alphaBuffer; - CARD32 alphaOffset; - CARD32 alphaPitch; - CARD32 alphaFormat; + CARD32 destFormat; + int destDepth; CARD32 textureLevel0Offset[VIA_NUM_TEXUNITS]; CARD32 textureLevel0Pitch[VIA_NUM_TEXUNITS]; CARD32 textureLevel0Exp[VIA_NUM_TEXUNITS]; @@ -208,6 +209,7 @@ typedef struct _Via3DState{ Bool textureCol[VIA_NUM_TEXUNITS]; Bool textureAlpha[VIA_NUM_TEXUNITS]; Bool agpTexture[VIA_NUM_TEXUNITS]; + Bool textureDirty[VIA_NUM_TEXUNITS]; int numTextures; Bool blend; Bool writeAlpha; @@ -282,6 +284,7 @@ typedef struct _VIA { XAAInfoRecPtr AccelInfoRec; ViaTwodContext td; Via3DState v3d; + Via3DState *lastToUpload; ViaCommandBuffer cb; int dgaMarker; CARD32 markerOffset; @@ -346,6 +349,9 @@ typedef struct _VIA { int drmVerMinor; int drmVerPL; VIAMem driOffScreenMem; + drm_via_mem_t texAGPBuffer; + unsigned texOffset; + char * texAddr; #endif Bool DRIIrqEnable; Bool agpEnable; @@ -419,6 +425,7 @@ void viaExitAccel(ScreenPtr); void viaDGABlitRect(ScrnInfoPtr, int, int, int, int, int, int); void viaDGAFillRect(ScrnInfoPtr, int, int, int, int, unsigned long); void viaDGAWaitMarker(ScrnInfoPtr); +void viaFinishInitAccel(ScreenPtr); /* In via_shadow.c */ void ViaShadowFBInit(ScrnInfoPtr pScrn, ScreenPtr pScreen); |