|
|
/*
** Copyright 1991,1992, Silicon Graphics, Inc. ** All Rights Reserved. ** ** This is UNPUBLISHED PROPRIETARY SOURCE CODE of Silicon Graphics, Inc.; ** the contents of this file may not be disclosed to third parties, copied or ** duplicated in any form, in whole or in part, without the prior written ** permission of Silicon Graphics, Inc. ** ** RESTRICTED RIGHTS LEGEND: ** Use, duplication or disclosure by the Government is subject to restrictions ** as set forth in subdivision (c)(1)(ii) of the Rights in Technical Data ** and Computer Software clause at DFARS 252.227-7013, and/or in similar or ** successor clauses in the FAR, DOD or NASA FAR Supplement. Unpublished - ** rights reserved under the Copyright Laws of the United States. ** */ #include "precomp.h"
#pragma hdrstop
#include <namesint.h>
void __glTexPriListRealize(__GLcontext *gc) { __GLtextureObject *high, *low; GLboolean tryUnload = GL_TRUE; MCDHANDLE loadKey; __GL_NAMES_ASSERT_LOCKED(gc->texture.shared->namesArray); // Attempt to load as many of the highest priority textures as
// possible. If a lower priority texture is resident and a
// higher priority texture is unable to load, kick it out
// and try again
high = gc->texture.shared->priorityListHighest; low = gc->texture.shared->priorityListLowest;
while (high != NULL) { // We only want to load textures that have image data
// Consider - Should check all mipmap levels?
if (high->loadKey == 0 && high->texture.map.level[0].buffer != NULL) { for (;;) { // If high == low then there are no longer any
// lower-priority textures to consider for unloading
if (high == low) { tryUnload = GL_FALSE; } loadKey = __glGenLoadTexture(gc, &high->texture.map, 0); if (loadKey != 0) { high->resident = GL_TRUE; high->loadKey = loadKey; break; }
if (tryUnload) { while (low->loadKey == 0 && low != high) { low = low->higherPriority; }
if (low->loadKey != 0) { __glGenFreeTexture(gc, &low->texture.map, low->loadKey); low->loadKey = 0; low->resident = GL_FALSE; } } else { break; } } }
high = high->lowerPriority; } }
void __glTexPriListAddToList(__GLcontext *gc, __GLtextureObject *texobj) { __GLtextureObject *texobjLower;
__GL_NAMES_ASSERT_LOCKED(gc->texture.shared->namesArray); // Walk the priority list to find a lower priority texture object
texobjLower = gc->texture.shared->priorityListHighest; while (texobjLower != NULL && texobjLower->texture.map.texobjs.priority > texobj->texture.map.texobjs.priority) { texobjLower = texobjLower->lowerPriority; }
if (texobjLower == NULL) { // Place at end of list
if (gc->texture.shared->priorityListLowest != NULL) { gc->texture.shared->priorityListLowest->lowerPriority = texobj; } else { gc->texture.shared->priorityListHighest = texobj; } texobj->higherPriority = gc->texture.shared->priorityListLowest; gc->texture.shared->priorityListLowest = texobj; } else { if (texobjLower->higherPriority != NULL) { texobjLower->higherPriority->lowerPriority = texobj; } else { gc->texture.shared->priorityListHighest = texobj; } texobj->higherPriority = texobjLower->higherPriority; texobjLower->higherPriority = texobj; } texobj->lowerPriority = texobjLower; }
void __glTexPriListAdd(__GLcontext *gc, __GLtextureObject *texobj, GLboolean realize) { __glNamesLockArray(gc, gc->texture.shared->namesArray); __glTexPriListAddToList(gc, texobj); if (realize) { __glTexPriListRealize(gc); }
__glNamesUnlockArray(gc, gc->texture.shared->namesArray); }
void __glTexPriListRemoveFromList(__GLcontext *gc, __GLtextureObject *texobj) { __GL_NAMES_ASSERT_LOCKED(gc->texture.shared->namesArray); #if DBG
{ __GLtextureObject *t;
for (t = gc->texture.shared->priorityListHighest; t != NULL; t = t->lowerPriority) { if (t == texobj) { break; } } ASSERTOPENGL(t != NULL, "Removing an unlisted texobj"); } #endif
if (texobj->higherPriority != NULL) { texobj->higherPriority->lowerPriority = texobj->lowerPriority; } else { gc->texture.shared->priorityListHighest = texobj->lowerPriority; } if (texobj->lowerPriority != NULL) { texobj->lowerPriority->higherPriority = texobj->higherPriority; } else { gc->texture.shared->priorityListLowest = texobj->higherPriority; } }
void __glTexPriListRemove(__GLcontext *gc, __GLtextureObject *texobj, GLboolean realize) { __glNamesLockArray(gc, gc->texture.shared->namesArray); __glTexPriListRemoveFromList(gc, texobj);
__glGenFreeTexture(gc, &texobj->texture.map, texobj->loadKey); texobj->loadKey = 0; texobj->resident = GL_FALSE;
if (realize) { __glTexPriListRealize(gc); }
__glNamesUnlockArray(gc, gc->texture.shared->namesArray); }
void __glTexPriListChangePriority(__GLcontext *gc, __GLtextureObject *texobj, GLboolean realize) { __glNamesLockArray(gc, gc->texture.shared->namesArray); __glTexPriListRemoveFromList(gc, texobj); __glTexPriListAddToList(gc, texobj);
// If we're re-realizing, don't bother calling the MCD texture-priority
// function:
if (realize) { __glTexPriListRealize(gc); } else if (((__GLGENcontext *)gc)->pMcdState && texobj->loadKey) { GenMcdUpdateTexturePriority((__GLGENcontext *)gc, &texobj->texture.map, texobj->loadKey); }
__glNamesUnlockArray(gc, gc->texture.shared->namesArray); }
void __glTexPriListLoadSubImage(__GLcontext *gc, GLenum target, GLint lod, GLint xoffset, GLint yoffset, GLsizei w, GLsizei h) { __GLtextureObject *pto;
// Always mark things as resident:
pto = __glLookUpTextureObject(gc, target); pto->resident = GL_TRUE; __glGenUpdateTexture(gc, &pto->texture.map, pto->loadKey);
// For MCD, send down the full subimage command:
if (((__GLGENcontext *)gc)->pMcdState && pto->loadKey) { GenMcdUpdateSubTexture((__GLGENcontext *)gc, &pto->texture.map, pto->loadKey, lod, xoffset, yoffset, w, h); } }
void __glTexPriListLoadImage(__GLcontext *gc, GLenum target) { __GLtextureObject *pto;
// If we're unaccelerated then always mark things as resident
pto = __glLookUpTextureObject(gc, target); pto->resident = GL_TRUE; __glGenUpdateTexture(gc, &pto->texture.map, pto->loadKey);
// For simplicity, we will assume that the texture size or format
// has changed, so delete the texture and re-realize the list.
//
// !!! If this becomes a performance issue, we *could* be smart about
// !!! detecting the cases where the texture size and format remains the
// !!! same. However, modifying a texture should really be done through
// !!! SubImage calls.
if (((__GLGENcontext *)gc)->pMcdState) { if (pto->loadKey) { GenMcdDeleteTexture((__GLGENcontext *)gc, pto->loadKey); pto->loadKey = 0; } __glNamesLockArray(gc, gc->texture.shared->namesArray); __glTexPriListRealize(gc); __glNamesUnlockArray(gc, gc->texture.shared->namesArray); } }
void __glTexPriListUnloadAll(__GLcontext *gc) { __GLtextureObject *texobj;
__GL_NAMES_ASSERT_LOCKED(gc->texture.shared->namesArray);
texobj = gc->texture.shared->priorityListHighest; while (texobj != NULL) { __glGenFreeTexture(gc, &texobj->texture.map, texobj->loadKey); texobj->loadKey = 0; texobj->resident = GL_FALSE;
texobj = texobj->lowerPriority; } }
|