X-Git-Url: https://git.libre-soc.org/?a=blobdiff_plain;f=src%2Fmesa%2Fdrivers%2Fglide%2Ffxtexman.c;h=940c8fd0b97d92c9d065b6b8753ae2a61a0193aa;hb=646ed82e6b2c092c6db364bf87d6881f39e83eec;hp=648649c0328206865f18841a5aeafe8cfa9084f0;hpb=a75246f8f5fa951d62b6b40db5bf47517b50d459;p=mesa.git diff --git a/src/mesa/drivers/glide/fxtexman.c b/src/mesa/drivers/glide/fxtexman.c index 648649c0328..940c8fd0b97 100644 --- a/src/mesa/drivers/glide/fxtexman.c +++ b/src/mesa/drivers/glide/fxtexman.c @@ -1,5 +1,3 @@ -/* $Id: fxtexman.c,v 1.17 2003/10/02 17:36:44 brianp Exp $ */ - /* * Mesa 3-D graphics library * Version: 4.0 @@ -42,9 +40,11 @@ #if defined(FX) +#include "hash.h" #include "fxdrv.h" int texSwaps = 0; +static FxU32 texBoundMask; #define FX_2MB_SPLIT 0x200000 @@ -116,43 +116,44 @@ fxTMNewRangeNode(fxMesaContext fxMesa, FxU32 start, FxU32 end) } else { if (!(result = MALLOC(sizeof(MemRange)))) { - fprintf(stderr, "%s: ERROR: out of memory!\n", __FUNCTION__); + fprintf(stderr, "fxTMNewRangeNode: ERROR: out of memory!\n"); fxCloseHardware(); exit(-1); } - result->next = NULL; } result->startAddr = start; result->endAddr = end; return result; } +#if 1 +#define fxTMDeleteRangeNode(fxMesa, range) \ + do { \ + range->next = fxMesa->tmPool; \ + fxMesa->tmPool = range; \ + } while (0); +#else static void fxTMDeleteRangeNode(fxMesaContext fxMesa, MemRange * range) { range->next = fxMesa->tmPool; fxMesa->tmPool = range; } +#endif static void fxTMUInit(fxMesaContext fxMesa, int tmu) { MemRange *tmn, *last; - FxU32 start, end, blockstart, blockend, boundary; + FxU32 start, end, blockstart, blockend, chunk; start = grTexMinAddress(tmu); end = grTexMaxAddress(tmu); - boundary = (fxMesa->type >= GR_SSTTYPE_Banshee) ? (end - start) : FX_2MB_SPLIT; - + chunk = (fxMesa->type >= GR_SSTTYPE_Banshee) ? (end - start) : FX_2MB_SPLIT; + if (fxMesa->verbose) { - fprintf(stderr, "Voodoo %s configuration:\n", - (tmu == FX_TMU0) ? "TMU0" : "TMU1"); - fprintf(stderr, "Voodoo Lower texture memory address (%u)\n", - (unsigned int) start); - fprintf(stderr, "Voodoo Higher texture memory address (%u)\n", - (unsigned int) end); - fprintf(stderr, "Voodoo Splitting Texture memory in %luMB blocks:\n", boundary >> 20); + fprintf(stderr, "Voodoo TMU%d configuration:\n", tmu); } fxMesa->freeTexMem[tmu] = end - start; @@ -161,16 +162,18 @@ fxTMUInit(fxMesaContext fxMesa, int tmu) last = 0; blockstart = start; while (blockstart < end) { - if (blockstart + boundary > end) + if (blockstart + chunk > end) blockend = end; else - blockend = blockstart + boundary; + blockend = blockstart + chunk; if (fxMesa->verbose) - fprintf(stderr, "Voodoo %07u-%07u\n", + fprintf(stderr, "Voodoo %08u-%08u\n", (unsigned int) blockstart, (unsigned int) blockend); tmn = fxTMNewRangeNode(fxMesa, blockstart, blockend); + tmn->next = NULL; + if (last) last->next = tmn; @@ -178,7 +181,7 @@ fxTMUInit(fxMesaContext fxMesa, int tmu) fxMesa->tmFree[tmu] = tmn; last = tmn; - blockstart += boundary; + blockstart += chunk; } } @@ -189,6 +192,10 @@ fxTMFindStartAddr(fxMesaContext fxMesa, GLint tmu, int size) int result; struct gl_texture_object *obj; + if (fxMesa->HaveTexUma) { + tmu = FX_TMU0; + } + while (1) { prev = 0; tmp = fxMesa->tmFree[tmu]; @@ -213,11 +220,11 @@ fxTMFindStartAddr(fxMesaContext fxMesa, GLint tmu, int size) } /* No free space. Discard oldest */ if (TDFX_DEBUG & VERBOSE_TEXTURE) { - fprintf(stderr, "%s: No free space. Discard oldest\n", __FUNCTION__); + fprintf(stderr, "fxTMFindStartAddr: No free space. Discard oldest\n"); } obj = fxTMFindOldestObject(fxMesa, tmu); if (!obj) { - fprintf(stderr, "%s: ERROR: No space for texture\n", __FUNCTION__); + fprintf(stderr, "fxTMFindStartAddr: ERROR: No space for texture\n"); return -1; } fxTMMoveOutTM(fxMesa, obj); @@ -225,11 +232,36 @@ fxTMFindStartAddr(fxMesaContext fxMesa, GLint tmu, int size) } } +int fxTMCheckStartAddr (fxMesaContext fxMesa, GLint tmu, tfxTexInfo *ti) +{ + MemRange *tmp; + int size; + + if (fxMesa->HaveTexUma) { + return FXTRUE; + } + + size = grTexTextureMemRequired(GR_MIPMAPLEVELMASK_BOTH, &(ti->info)); + + tmp = fxMesa->tmFree[tmu]; + while (tmp) { + if (tmp->endAddr - tmp->startAddr >= size) { /* Fits here */ + return FXTRUE; + } + tmp = tmp->next; + } + + return FXFALSE; +} + static void fxTMRemoveRange(fxMesaContext fxMesa, GLint tmu, MemRange * range) { MemRange *tmp, *prev; - FxU32 boundary = (fxMesa->type >= GR_SSTTYPE_Banshee) ? -1 : (FX_2MB_SPLIT - 1); + + if (fxMesa->HaveTexUma) { + tmu = FX_TMU0; + } if (range->startAddr == range->endAddr) { fxTMDeleteRangeNode(fxMesa, range); @@ -252,7 +284,7 @@ fxTMRemoveRange(fxMesaContext fxMesa, GLint tmu, MemRange * range) range->next = tmp; if (tmp) { if (range->endAddr == tmp->startAddr - && tmp->startAddr & boundary) { + && tmp->startAddr & texBoundMask) { /* Combine */ tmp->startAddr = range->startAddr; fxTMDeleteRangeNode(fxMesa, range); @@ -261,7 +293,7 @@ fxTMRemoveRange(fxMesaContext fxMesa, GLint tmu, MemRange * range) } if (prev) { if (prev->endAddr == range->startAddr - && range->startAddr & boundary) { + && range->startAddr & texBoundMask) { /* Combine */ prev->endAddr = range->endAddr; prev->next = range->next; @@ -280,12 +312,13 @@ fxTMFindOldestObject(fxMesaContext fxMesa, int tmu) { GLuint age, old, lasttime, bindnumber; GLfloat lowestPriority; - tfxTexInfo *info; - struct gl_texture_object *obj, *tmp, *lowestPriorityObj; + struct gl_texture_object *obj, *lowestPriorityObj; + struct _mesa_HashTable *textures = fxMesa->glCtx->Shared->TexObjects; + GLuint id; - tmp = fxMesa->glCtx->Shared->TexObjectList; - if (!tmp) + if (!_mesa_HashFirstEntry(textures)) return 0; + obj = NULL; old = 0; @@ -293,12 +326,21 @@ fxTMFindOldestObject(fxMesaContext fxMesa, int tmu) lowestPriority = 1.0F; bindnumber = fxMesa->texBindNumber; - while (tmp) { - info = fxTMGetTexInfo(tmp); + + for (id = _mesa_HashFirstEntry(textures); + id; + id = _mesa_HashNextEntry(textures, id)) { + struct gl_texture_object *tmp + = (struct gl_texture_object *) _mesa_HashLookup(textures, id); + tfxTexInfo *info = fxTMGetTexInfo(tmp); if (info && info->isInTM && - ((info->whichTMU == tmu) || (info->whichTMU == FX_TMU_BOTH) || - (info->whichTMU == FX_TMU_SPLIT))) { + ((info->whichTMU == tmu) || + (info->whichTMU == FX_TMU_BOTH) || + (info->whichTMU == FX_TMU_SPLIT) || + fxMesa->HaveTexUma + ) + ) { lasttime = info->lastTimeUsed; if (lasttime > bindnumber) @@ -312,16 +354,14 @@ fxTMFindOldestObject(fxMesaContext fxMesa, int tmu) } /* examine priority */ - if (obj->Priority < lowestPriority) { + if (tmp->Priority < lowestPriority) { lowestPriority = tmp->Priority; lowestPriorityObj = tmp; } } - tmp = tmp->Next; } - if (lowestPriority < 1.0) { - ASSERT(lowestPriorityObj); + if (lowestPriorityObj != NULL) { if (TDFX_DEBUG & VERBOSE_TEXTURE) { fprintf(stderr, "fxTMFindOldestObject: %d pri=%f\n", lowestPriorityObj->Name, lowestPriority); } @@ -329,7 +369,9 @@ fxTMFindOldestObject(fxMesaContext fxMesa, int tmu) } else { if (TDFX_DEBUG & VERBOSE_TEXTURE) { - fprintf(stderr, "fxTMFindOldestObject: %d age=%d\n", obj->Name, old); + if (obj != NULL) { + fprintf(stderr, "fxTMFindOldestObject: %d age=%d\n", obj->Name, old); + } } return obj; } @@ -360,13 +402,13 @@ fxTMMoveInTM_NoLock(fxMesaContext fxMesa, struct gl_texture_object *tObj, int texmemsize; if (TDFX_DEBUG & VERBOSE_DRIVER) { - fprintf(stderr, "%s(%d)\n", __FUNCTION__, tObj->Name); + fprintf(stderr, "fxTMMoveInTM_NoLock(%d)\n", tObj->Name); } fxMesa->stats.reqTexUpload++; if (!ti->validated) { - fprintf(stderr, "%s: INTERNAL ERROR: not validated\n", __FUNCTION__); + fprintf(stderr, "fxTMMoveInTM_NoLock: INTERNAL ERROR: not validated\n"); fxCloseHardware(); exit(-1); } @@ -384,8 +426,8 @@ fxTMMoveInTM_NoLock(fxMesaContext fxMesa, struct gl_texture_object *tObj, } if (TDFX_DEBUG & (VERBOSE_DRIVER | VERBOSE_TEXTURE)) { - fprintf(stderr, "%s: downloading %p (%d) in texture memory in %d\n", - __FUNCTION__, (void *)tObj, tObj->Name, where); + fprintf(stderr, "fxTMMoveInTM_NoLock: downloading %p (%d) in texture memory in %d\n", + (void *)tObj, tObj->Name, where); } ti->whichTMU = (FxU32) where; @@ -399,7 +441,7 @@ fxTMMoveInTM_NoLock(fxMesaContext fxMesa, struct gl_texture_object *tObj, for (i = FX_largeLodValue(ti->info), l = ti->minLevel; i <= FX_smallLodValue(ti->info); i++, l++) { - struct gl_texture_image *texImage = tObj->Image[l]; + struct gl_texture_image *texImage = tObj->Image[0][l]; grTexDownloadMipMapLevel(where, ti->tm[where]->startAddr, FX_valueToLod(i), @@ -421,7 +463,7 @@ fxTMMoveInTM_NoLock(fxMesaContext fxMesa, struct gl_texture_object *tObj, for (i = FX_largeLodValue(ti->info), l = ti->minLevel; i <= FX_smallLodValue(ti->info); i++, l++) { - struct gl_texture_image *texImage = tObj->Image[l]; + struct gl_texture_image *texImage = tObj->Image[0][l]; grTexDownloadMipMapLevel(GR_TMU0, ti->tm[FX_TMU0]->startAddr, @@ -449,11 +491,11 @@ fxTMMoveInTM_NoLock(fxMesaContext fxMesa, struct gl_texture_object *tObj, /*texmemsize = (int)grTexTextureMemRequired(GR_MIPMAPLEVELMASK_BOTH, &(ti->info));*/ ti->tm[FX_TMU1] = fxTMAddObj(fxMesa, tObj, FX_TMU1, texmemsize); - fxMesa->stats.memTexUpload += texmemsize; /* ZZZ: required? */ + fxMesa->stats.memTexUpload += texmemsize; for (i = FX_largeLodValue(ti->info), l = ti->minLevel; i <= FX_smallLodValue(ti->info); i++, l++) { - struct gl_texture_image *texImage = tObj->Image[l]; + struct gl_texture_image *texImage = tObj->Image[0][l]; grTexDownloadMipMapLevel(GR_TMU0, ti->tm[FX_TMU0]->startAddr, FX_valueToLod(i), @@ -474,7 +516,7 @@ fxTMMoveInTM_NoLock(fxMesaContext fxMesa, struct gl_texture_object *tObj, } break; default: - fprintf(stderr, "%s: INTERNAL ERROR: wrong tmu (%d)\n", __FUNCTION__, where); + fprintf(stderr, "fxTMMoveInTM_NoLock: INTERNAL ERROR: wrong tmu (%d)\n", where); fxCloseHardware(); exit(-1); } @@ -502,7 +544,7 @@ fxTMReloadMipMapLevel(fxMesaContext fxMesa, struct gl_texture_object *tObj, tfxTexInfo *ti = fxTMGetTexInfo(tObj); GrLOD_t lodlevel; GLint tmu; - struct gl_texture_image *texImage = tObj->Image[level]; + struct gl_texture_image *texImage = tObj->Image[0][level]; tfxMipMapLevel *mml = FX_MIPMAP_DATA(texImage); if (TDFX_DEBUG & VERBOSE_TEXTURE) { @@ -513,15 +555,17 @@ fxTMReloadMipMapLevel(fxMesaContext fxMesa, struct gl_texture_object *tObj, assert(mml->width > 0); assert(mml->height > 0); assert(mml->glideFormat > 0); + assert(ti->isInTM); if (!ti->validated) { - fprintf(stderr, "%s: INTERNAL ERROR: not validated\n", __FUNCTION__); + fprintf(stderr, "fxTMReloadMipMapLevel: INTERNAL ERROR: not validated\n"); fxCloseHardware(); exit(-1); } tmu = (int) ti->whichTMU; - fxTMMoveInTM(fxMesa, tObj, tmu); + fxMesa->stats.reqTexUpload++; + fxMesa->stats.texUpload++; lodlevel = ti->info.largeLodLog2 - (level - ti->minLevel); @@ -572,7 +616,7 @@ fxTMReloadMipMapLevel(fxMesaContext fxMesa, struct gl_texture_object *tObj, break; default: - fprintf(stderr, "%s: INTERNAL ERROR: wrong tmu (%d)\n", __FUNCTION__, tmu); + fprintf(stderr, "fxTMReloadMipMapLevel: INTERNAL ERROR: wrong tmu (%d)\n", tmu); fxCloseHardware(); exit(-1); } @@ -587,13 +631,13 @@ fxTMReloadSubMipMapLevel(fxMesaContext fxMesa, GrLOD_t lodlevel; unsigned short *data; GLint tmu; - struct gl_texture_image *texImage = tObj->Image[level]; + struct gl_texture_image *texImage = tObj->Image[0][level]; tfxMipMapLevel *mml = FX_MIPMAP_DATA(texImage); assert(mml); if (!ti->validated) { - fprintf(stderr, "%s: INTERNAL ERROR: not validated\n", __FUNCTION__); + fprintf(stderr, "fxTMReloadSubMipMapLevel: INTERNAL ERROR: not validated\n"); fxCloseHardware(); exit(-1); } @@ -667,7 +711,7 @@ fxTMReloadSubMipMapLevel(fxMesaContext fxMesa, yoffset, yoffset + height - 1); break; default: - fprintf(stderr, "%s: INTERNAL ERROR: wrong tmu (%d)\n", __FUNCTION__, tmu); + fprintf(stderr, "fxTMReloadSubMipMapLevel: INTERNAL ERROR: wrong tmu (%d)\n", tmu); fxCloseHardware(); exit(-1); } @@ -679,7 +723,7 @@ fxTMMoveOutTM(fxMesaContext fxMesa, struct gl_texture_object *tObj) tfxTexInfo *ti = fxTMGetTexInfo(tObj); if (TDFX_DEBUG & VERBOSE_DRIVER) { - fprintf(stderr, "%s(%p (%d))\n", __FUNCTION__, (void *)tObj, tObj->Name); + fprintf(stderr, "fxTMMoveOutTM(%p (%d))\n", (void *)tObj, tObj->Name); } if (!ti->isInTM) @@ -696,7 +740,7 @@ fxTMMoveOutTM(fxMesaContext fxMesa, struct gl_texture_object *tObj) fxTMRemoveRange(fxMesa, FX_TMU1, ti->tm[FX_TMU1]); break; default: - fprintf(stderr, "%s: INTERNAL ERROR: bad TMU (%ld)\n", __FUNCTION__, ti->whichTMU); + fprintf(stderr, "fxTMMoveOutTM: INTERNAL ERROR: bad TMU (%ld)\n", ti->whichTMU); fxCloseHardware(); exit(-1); } @@ -712,18 +756,14 @@ fxTMFreeTexture(fxMesaContext fxMesa, struct gl_texture_object *tObj) int i; if (TDFX_DEBUG & VERBOSE_TEXTURE) { - fprintf(stderr, "%s(%p (%d))\n", __FUNCTION__, (void *)tObj, tObj->Name); + fprintf(stderr, "fxTMFreeTexture(%p (%d))\n", (void *)tObj, tObj->Name); } fxTMMoveOutTM(fxMesa, tObj); for (i = 0; i < MAX_TEXTURE_LEVELS; i++) { - struct gl_texture_image *texImage = tObj->Image[i]; + struct gl_texture_image *texImage = tObj->Image[0][i]; if (texImage) { - if (texImage->Data) { - MESA_PBUFFER_FREE(texImage->Data); - texImage->Data = NULL; - } if (texImage->DriverData) { FREE(texImage->DriverData); texImage->DriverData = NULL; @@ -749,10 +789,16 @@ fxTMInit(fxMesaContext fxMesa) fxMesa->texBindNumber = 0; fxMesa->tmPool = 0; + if (fxMesa->HaveTexUma) { + grEnable(GR_TEXTURE_UMA_EXT); + } + fxTMUInit(fxMesa, FX_TMU0); - if (fxMesa->haveTwoTMUs) + if (!fxMesa->HaveTexUma && fxMesa->haveTwoTMUs) fxTMUInit(fxMesa, FX_TMU1); + + texBoundMask = (fxMesa->type >= GR_SSTTYPE_Banshee) ? -1 : (FX_2MB_SPLIT - 1); } void @@ -785,26 +831,29 @@ fxTMClose(fxMesaContext fxMesa) void fxTMRestoreTextures_NoLock(fxMesaContext ctx) { - tfxTexInfo *ti; - struct gl_texture_object *tObj; - int i, where; - - tObj = ctx->glCtx->Shared->TexObjectList; - while (tObj) { - ti = fxTMGetTexInfo(tObj); + struct _mesa_HashTable *textures = ctx->glCtx->Shared->TexObjects; + GLuint id; + + for (id = _mesa_HashFirstEntry(textures); + id; + id = _mesa_HashNextEntry(textures, id)) { + struct gl_texture_object *tObj + = (struct gl_texture_object *) _mesa_HashLookup(textures, id); + tfxTexInfo *ti = fxTMGetTexInfo(tObj); if (ti && ti->isInTM) { - for (i = 0; i < MAX_TEXTURE_UNITS; i++) + int i; + for (i = 0; i < MAX_TEXTURE_UNITS; i++) { if (ctx->glCtx->Texture.Unit[i]._Current == tObj) { /* Force the texture onto the board, as it could be in use */ - where = ti->whichTMU; + int where = ti->whichTMU; fxTMMoveOutTM_NoLock(ctx, tObj); fxTMMoveInTM_NoLock(ctx, tObj, where); break; } + } if (i == MAX_TEXTURE_UNITS) /* Mark the texture as off the board */ fxTMMoveOutTM_NoLock(ctx, tObj); } - tObj = tObj->Next; } }