From cb324339038cff26ac69eb8dc456a0335cb36194 Mon Sep 17 00:00:00 2001 From: Owen W. Taylor Date: Sun, 6 Apr 2008 13:30:41 -0400 Subject: [PATCH] Further repeat fixes for R100 + R200 - We need to tile in both directions if either is NPOT - It's OK to repeat even if the pixmap is padded (pitch > width) --- src/radeon_exa_render.c | 36 +++++++++++++++++++----------------- 1 files changed, 19 insertions(+), 17 deletions(-) diff --git a/src/radeon_exa_render.c b/src/radeon_exa_render.c index 923fae3..8d7ff9b 100644 --- a/src/radeon_exa_render.c +++ b/src/radeon_exa_render.c @@ -240,16 +240,28 @@ static Bool RADEONCheckTexturePOT(PicturePtr pPict, Bool canTile) * by drawing the image in multiple tiles. (A common case that it's * important to get right is drawing a strip of a NPOTxPOT texture * repeating in the POT direction. With tiling, this ends up as a - * a single tile, which is perfect.) + * a single tile on R300 and newer, which is perfect.) */ -static Bool RADEONSetupSourceTile(PicturePtr pPict) +static Bool RADEONSetupSourceTile(PicturePtr pPict, + Bool canTile1d) { if (pPict->repeat && !pPict->transform) { int w = pPict->pDrawable->width; int h = pPict->pDrawable->height; - need_src_tile_x = (w & (w - 1)) != 0; - need_src_tile_y = (h & (h - 1)) != 0; + /* On R300 and newer, we can repeat a texture that is NPOT in + * one direction and POT in the other in the POT direction; on + * older chips we can only repeat at all if the texture is POT in + * both directions. + */ + if (canTile1d) { + need_src_tile_x = (w & (w - 1)) != 0; + need_src_tile_y = (h & (h - 1)) != 0; + } else { + need_src_tile_x = need_src_tile_y = + (w & (w - 1)) != 0 || (h & (h - 1)) != 0; + } + } else { need_src_tile_x = FALSE; need_src_tile_y = FALSE; @@ -319,11 +331,6 @@ static Bool FUNC_NAME(R100TextureSetup)(PicturePtr pPict, PixmapPtr pPix, txoffset |= RADEON_TXO_MACRO_TILE; if (pPict->repeat) { - if ((h != 1) && - (((w * pPix->drawable.bitsPerPixel / 8 + 31) & ~31) != txpitch)) - RADEON_FALLBACK(("Width %d and pitch %u not compatible for repeat\n", - w, (unsigned)txpitch)); - txformat |= RADEONLog2(w) << RADEON_TXFORMAT_WIDTH_SHIFT; txformat |= RADEONLog2(h) << RADEON_TXFORMAT_HEIGHT_SHIFT; } else @@ -496,7 +503,7 @@ static Bool FUNC_NAME(R100PrepareComposite)(int op, if (((dst_pitch >> pixel_shift) & 0x7) != 0) RADEON_FALLBACK(("Bad destination pitch 0x%x\n", (int)dst_pitch)); - if (!RADEONSetupSourceTile(pSrcPicture)) + if (!RADEONSetupSourceTile(pSrcPicture, FALSE)) return FALSE; if (!FUNC_NAME(R100TextureSetup)(pSrcPicture, pSrc, 0)) @@ -626,11 +633,6 @@ static Bool FUNC_NAME(R200TextureSetup)(PicturePtr pPict, PixmapPtr pPix, txoffset |= R200_TXO_MACRO_TILE; if (pPict->repeat) { - if ((h != 1) && - (((w * pPix->drawable.bitsPerPixel / 8 + 31) & ~31) != txpitch)) - RADEON_FALLBACK(("Width %d and pitch %u not compatible for repeat\n", - w, (unsigned)txpitch)); - txformat |= RADEONLog2(w) << R200_TXFORMAT_WIDTH_SHIFT; txformat |= RADEONLog2(h) << R200_TXFORMAT_HEIGHT_SHIFT; } else @@ -787,7 +789,7 @@ static Bool FUNC_NAME(R200PrepareComposite)(int op, PicturePtr pSrcPicture, if (((dst_pitch >> pixel_shift) & 0x7) != 0) RADEON_FALLBACK(("Bad destination pitch 0x%x\n", (int)dst_pitch)); - if (!RADEONSetupSourceTile(pSrcPicture)) + if (!RADEONSetupSourceTile(pSrcPicture, FALSE)) return FALSE; if (!FUNC_NAME(R200TextureSetup)(pSrcPicture, pSrc, 0)) @@ -1136,7 +1138,7 @@ static Bool FUNC_NAME(R300PrepareComposite)(int op, PicturePtr pSrcPicture, if (((dst_pitch >> pixel_shift) & 0x7) != 0) RADEON_FALLBACK(("Bad destination pitch 0x%x\n", (int)dst_pitch)); - if (!RADEONSetupSourceTile(pSrcPicture)) + if (!RADEONSetupSourceTile(pSrcPicture, TRUE)) return FALSE; if (!FUNC_NAME(R300TextureSetup)(pSrcPicture, pSrc, 0)) -- 1.5.4.5