texstate.c revision 56e89960
17117f1b4Smrg/* 27117f1b4Smrg * Mesa 3-D graphics library 356e89960Smrg * Version: 7.5 47117f1b4Smrg * 57117f1b4Smrg * Copyright (C) 1999-2007 Brian Paul All Rights Reserved. 67117f1b4Smrg * 77117f1b4Smrg * Permission is hereby granted, free of charge, to any person obtaining a 87117f1b4Smrg * copy of this software and associated documentation files (the "Software"), 97117f1b4Smrg * to deal in the Software without restriction, including without limitation 107117f1b4Smrg * the rights to use, copy, modify, merge, publish, distribute, sublicense, 117117f1b4Smrg * and/or sell copies of the Software, and to permit persons to whom the 127117f1b4Smrg * Software is furnished to do so, subject to the following conditions: 137117f1b4Smrg * 147117f1b4Smrg * The above copyright notice and this permission notice shall be included 157117f1b4Smrg * in all copies or substantial portions of the Software. 167117f1b4Smrg * 177117f1b4Smrg * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 187117f1b4Smrg * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 197117f1b4Smrg * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 207117f1b4Smrg * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN 217117f1b4Smrg * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 227117f1b4Smrg * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 237117f1b4Smrg */ 247117f1b4Smrg 257117f1b4Smrg/** 267117f1b4Smrg * \file texstate.c 277117f1b4Smrg * 287117f1b4Smrg * Texture state handling. 297117f1b4Smrg */ 307117f1b4Smrg 317117f1b4Smrg#include "glheader.h" 3256e89960Smrg#include "mfeatures.h" 337117f1b4Smrg#include "colormac.h" 347117f1b4Smrg#include "colortab.h" 357117f1b4Smrg#include "context.h" 367117f1b4Smrg#include "enums.h" 377117f1b4Smrg#include "macros.h" 387117f1b4Smrg#include "texobj.h" 397117f1b4Smrg#include "teximage.h" 407117f1b4Smrg#include "texstate.h" 417117f1b4Smrg#include "mtypes.h" 427117f1b4Smrg 437117f1b4Smrg 447117f1b4Smrg 457117f1b4Smrg/** 467117f1b4Smrg * Default texture combine environment state. This is used to initialize 477117f1b4Smrg * a context's texture units and as the basis for converting "classic" 487117f1b4Smrg * texture environmnets to ARB_texture_env_combine style values. 497117f1b4Smrg */ 507117f1b4Smrgstatic const struct gl_tex_env_combine_state default_combine_state = { 517117f1b4Smrg GL_MODULATE, GL_MODULATE, 5256e89960Smrg { GL_TEXTURE, GL_PREVIOUS, GL_CONSTANT, GL_CONSTANT }, 5356e89960Smrg { GL_TEXTURE, GL_PREVIOUS, GL_CONSTANT, GL_CONSTANT }, 5456e89960Smrg { GL_SRC_COLOR, GL_SRC_COLOR, GL_SRC_ALPHA, GL_SRC_ALPHA }, 5556e89960Smrg { GL_SRC_ALPHA, GL_SRC_ALPHA, GL_SRC_ALPHA, GL_SRC_ALPHA }, 567117f1b4Smrg 0, 0, 577117f1b4Smrg 2, 2 587117f1b4Smrg}; 597117f1b4Smrg 607117f1b4Smrg 617117f1b4Smrg 627117f1b4Smrg/** 637117f1b4Smrg * Used by glXCopyContext to copy texture state from one context to another. 647117f1b4Smrg */ 657117f1b4Smrgvoid 667117f1b4Smrg_mesa_copy_texture_state( const GLcontext *src, GLcontext *dst ) 677117f1b4Smrg{ 6856e89960Smrg GLuint u, tex; 697117f1b4Smrg 707117f1b4Smrg ASSERT(src); 717117f1b4Smrg ASSERT(dst); 727117f1b4Smrg 737117f1b4Smrg dst->Texture.CurrentUnit = src->Texture.CurrentUnit; 747117f1b4Smrg dst->Texture._GenFlags = src->Texture._GenFlags; 757117f1b4Smrg dst->Texture._TexGenEnabled = src->Texture._TexGenEnabled; 767117f1b4Smrg dst->Texture._TexMatEnabled = src->Texture._TexMatEnabled; 777117f1b4Smrg dst->Texture.SharedPalette = src->Texture.SharedPalette; 787117f1b4Smrg 797117f1b4Smrg /* per-unit state */ 8056e89960Smrg for (u = 0; u < src->Const.MaxTextureImageUnits; u++) { 8156e89960Smrg dst->Texture.Unit[u].Enabled = src->Texture.Unit[u].Enabled; 8256e89960Smrg dst->Texture.Unit[u].EnvMode = src->Texture.Unit[u].EnvMode; 8356e89960Smrg COPY_4V(dst->Texture.Unit[u].EnvColor, src->Texture.Unit[u].EnvColor); 8456e89960Smrg dst->Texture.Unit[u].TexGenEnabled = src->Texture.Unit[u].TexGenEnabled; 8556e89960Smrg dst->Texture.Unit[u].GenS = src->Texture.Unit[u].GenS; 8656e89960Smrg dst->Texture.Unit[u].GenT = src->Texture.Unit[u].GenT; 8756e89960Smrg dst->Texture.Unit[u].GenR = src->Texture.Unit[u].GenR; 8856e89960Smrg dst->Texture.Unit[u].GenQ = src->Texture.Unit[u].GenQ; 8956e89960Smrg dst->Texture.Unit[u].LodBias = src->Texture.Unit[u].LodBias; 907117f1b4Smrg 917117f1b4Smrg /* GL_EXT_texture_env_combine */ 9256e89960Smrg dst->Texture.Unit[u].Combine = src->Texture.Unit[u].Combine; 937117f1b4Smrg 9456e89960Smrg /* GL_ATI_envmap_bumpmap - need this? */ 9556e89960Smrg dst->Texture.Unit[u].BumpTarget = src->Texture.Unit[u].BumpTarget; 9656e89960Smrg COPY_4V(dst->Texture.Unit[u].RotMatrix, src->Texture.Unit[u].RotMatrix); 9756e89960Smrg 9856e89960Smrg /* 9956e89960Smrg * XXX strictly speaking, we should compare texture names/ids and 10056e89960Smrg * bind textures in the dest context according to id. For now, only 10156e89960Smrg * copy bindings if the contexts share the same pool of textures to 10256e89960Smrg * avoid refcounting bugs. 10356e89960Smrg */ 10456e89960Smrg if (dst->Shared == src->Shared) { 10556e89960Smrg /* copy texture object bindings, not contents of texture objects */ 10656e89960Smrg _mesa_lock_context_textures(dst); 1077117f1b4Smrg 10856e89960Smrg for (tex = 0; tex < NUM_TEXTURE_TARGETS; tex++) { 10956e89960Smrg _mesa_reference_texobj(&dst->Texture.Unit[u].CurrentTex[tex], 11056e89960Smrg src->Texture.Unit[u].CurrentTex[tex]); 11156e89960Smrg } 11256e89960Smrg _mesa_unlock_context_textures(dst); 11356e89960Smrg } 1147117f1b4Smrg } 1157117f1b4Smrg} 1167117f1b4Smrg 1177117f1b4Smrg 1187117f1b4Smrg/* 1197117f1b4Smrg * For debugging 1207117f1b4Smrg */ 1217117f1b4Smrgvoid 1227117f1b4Smrg_mesa_print_texunit_state( GLcontext *ctx, GLuint unit ) 1237117f1b4Smrg{ 1247117f1b4Smrg const struct gl_texture_unit *texUnit = ctx->Texture.Unit + unit; 1257117f1b4Smrg _mesa_printf("Texture Unit %d\n", unit); 1267117f1b4Smrg _mesa_printf(" GL_TEXTURE_ENV_MODE = %s\n", _mesa_lookup_enum_by_nr(texUnit->EnvMode)); 1277117f1b4Smrg _mesa_printf(" GL_COMBINE_RGB = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.ModeRGB)); 1287117f1b4Smrg _mesa_printf(" GL_COMBINE_ALPHA = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.ModeA)); 1297117f1b4Smrg _mesa_printf(" GL_SOURCE0_RGB = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.SourceRGB[0])); 1307117f1b4Smrg _mesa_printf(" GL_SOURCE1_RGB = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.SourceRGB[1])); 1317117f1b4Smrg _mesa_printf(" GL_SOURCE2_RGB = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.SourceRGB[2])); 1327117f1b4Smrg _mesa_printf(" GL_SOURCE0_ALPHA = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.SourceA[0])); 1337117f1b4Smrg _mesa_printf(" GL_SOURCE1_ALPHA = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.SourceA[1])); 1347117f1b4Smrg _mesa_printf(" GL_SOURCE2_ALPHA = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.SourceA[2])); 1357117f1b4Smrg _mesa_printf(" GL_OPERAND0_RGB = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.OperandRGB[0])); 1367117f1b4Smrg _mesa_printf(" GL_OPERAND1_RGB = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.OperandRGB[1])); 1377117f1b4Smrg _mesa_printf(" GL_OPERAND2_RGB = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.OperandRGB[2])); 1387117f1b4Smrg _mesa_printf(" GL_OPERAND0_ALPHA = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.OperandA[0])); 1397117f1b4Smrg _mesa_printf(" GL_OPERAND1_ALPHA = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.OperandA[1])); 1407117f1b4Smrg _mesa_printf(" GL_OPERAND2_ALPHA = %s\n", _mesa_lookup_enum_by_nr(texUnit->Combine.OperandA[2])); 1417117f1b4Smrg _mesa_printf(" GL_RGB_SCALE = %d\n", 1 << texUnit->Combine.ScaleShiftRGB); 1427117f1b4Smrg _mesa_printf(" GL_ALPHA_SCALE = %d\n", 1 << texUnit->Combine.ScaleShiftA); 1437117f1b4Smrg _mesa_printf(" GL_TEXTURE_ENV_COLOR = (%f, %f, %f, %f)\n", texUnit->EnvColor[0], texUnit->EnvColor[1], texUnit->EnvColor[2], texUnit->EnvColor[3]); 144c1f859d4Smrg} 1457117f1b4Smrg 1467117f1b4Smrg 1477117f1b4Smrg 148c1f859d4Smrg/**********************************************************************/ 149c1f859d4Smrg/* Texture Environment */ 150c1f859d4Smrg/**********************************************************************/ 1517117f1b4Smrg 152c1f859d4Smrg/** 153c1f859d4Smrg * Convert "classic" texture environment to ARB_texture_env_combine style 154c1f859d4Smrg * environments. 155c1f859d4Smrg * 156c1f859d4Smrg * \param state texture_env_combine state vector to be filled-in. 157c1f859d4Smrg * \param mode Classic texture environment mode (i.e., \c GL_REPLACE, 158c1f859d4Smrg * \c GL_BLEND, \c GL_DECAL, etc.). 159c1f859d4Smrg * \param texBaseFormat Base format of the texture associated with the 160c1f859d4Smrg * texture unit. 161c1f859d4Smrg */ 162c1f859d4Smrgstatic void 163c1f859d4Smrgcalculate_derived_texenv( struct gl_tex_env_combine_state *state, 164c1f859d4Smrg GLenum mode, GLenum texBaseFormat ) 165c1f859d4Smrg{ 166c1f859d4Smrg GLenum mode_rgb; 167c1f859d4Smrg GLenum mode_a; 1687117f1b4Smrg 169c1f859d4Smrg *state = default_combine_state; 1707117f1b4Smrg 171c1f859d4Smrg switch (texBaseFormat) { 172c1f859d4Smrg case GL_ALPHA: 173c1f859d4Smrg state->SourceRGB[0] = GL_PREVIOUS; 174c1f859d4Smrg break; 1757117f1b4Smrg 176c1f859d4Smrg case GL_LUMINANCE_ALPHA: 177c1f859d4Smrg case GL_INTENSITY: 178c1f859d4Smrg case GL_RGBA: 179c1f859d4Smrg break; 1807117f1b4Smrg 181c1f859d4Smrg case GL_LUMINANCE: 182c1f859d4Smrg case GL_RGB: 183c1f859d4Smrg case GL_YCBCR_MESA: 18456e89960Smrg case GL_DUDV_ATI: 185c1f859d4Smrg state->SourceA[0] = GL_PREVIOUS; 186c1f859d4Smrg break; 187c1f859d4Smrg 188c1f859d4Smrg default: 18956e89960Smrg _mesa_problem(NULL, 19056e89960Smrg "Invalid texBaseFormat 0x%x in calculate_derived_texenv", 19156e89960Smrg texBaseFormat); 1927117f1b4Smrg return; 1937117f1b4Smrg } 1947117f1b4Smrg 195c1f859d4Smrg if (mode == GL_REPLACE_EXT) 196c1f859d4Smrg mode = GL_REPLACE; 1977117f1b4Smrg 198c1f859d4Smrg switch (mode) { 199c1f859d4Smrg case GL_REPLACE: 200c1f859d4Smrg case GL_MODULATE: 201c1f859d4Smrg mode_rgb = (texBaseFormat == GL_ALPHA) ? GL_REPLACE : mode; 202c1f859d4Smrg mode_a = mode; 203c1f859d4Smrg break; 204c1f859d4Smrg 205c1f859d4Smrg case GL_DECAL: 206c1f859d4Smrg mode_rgb = GL_INTERPOLATE; 207c1f859d4Smrg mode_a = GL_REPLACE; 208c1f859d4Smrg 209c1f859d4Smrg state->SourceA[0] = GL_PREVIOUS; 210c1f859d4Smrg 211c1f859d4Smrg /* Having alpha / luminance / intensity textures replace using the 212c1f859d4Smrg * incoming fragment color matches the definition in NV_texture_shader. 213c1f859d4Smrg * The 1.5 spec simply marks these as "undefined". 214c1f859d4Smrg */ 215c1f859d4Smrg switch (texBaseFormat) { 216c1f859d4Smrg case GL_ALPHA: 217c1f859d4Smrg case GL_LUMINANCE: 218c1f859d4Smrg case GL_LUMINANCE_ALPHA: 219c1f859d4Smrg case GL_INTENSITY: 220c1f859d4Smrg state->SourceRGB[0] = GL_PREVIOUS; 2217117f1b4Smrg break; 222c1f859d4Smrg case GL_RGB: 223c1f859d4Smrg case GL_YCBCR_MESA: 22456e89960Smrg case GL_DUDV_ATI: 225c1f859d4Smrg mode_rgb = GL_REPLACE; 2267117f1b4Smrg break; 227c1f859d4Smrg case GL_RGBA: 228c1f859d4Smrg state->SourceRGB[2] = GL_TEXTURE; 2297117f1b4Smrg break; 230c1f859d4Smrg } 231c1f859d4Smrg break; 2327117f1b4Smrg 233c1f859d4Smrg case GL_BLEND: 234c1f859d4Smrg mode_rgb = GL_INTERPOLATE; 235c1f859d4Smrg mode_a = GL_MODULATE; 2367117f1b4Smrg 237c1f859d4Smrg switch (texBaseFormat) { 238c1f859d4Smrg case GL_ALPHA: 239c1f859d4Smrg mode_rgb = GL_REPLACE; 240c1f859d4Smrg break; 241c1f859d4Smrg case GL_INTENSITY: 242c1f859d4Smrg mode_a = GL_INTERPOLATE; 243c1f859d4Smrg state->SourceA[0] = GL_CONSTANT; 244c1f859d4Smrg state->OperandA[2] = GL_SRC_ALPHA; 245c1f859d4Smrg /* FALLTHROUGH */ 246c1f859d4Smrg case GL_LUMINANCE: 247c1f859d4Smrg case GL_RGB: 248c1f859d4Smrg case GL_LUMINANCE_ALPHA: 249c1f859d4Smrg case GL_RGBA: 250c1f859d4Smrg case GL_YCBCR_MESA: 25156e89960Smrg case GL_DUDV_ATI: 252c1f859d4Smrg state->SourceRGB[2] = GL_TEXTURE; 253c1f859d4Smrg state->SourceA[2] = GL_TEXTURE; 254c1f859d4Smrg state->SourceRGB[0] = GL_CONSTANT; 255c1f859d4Smrg state->OperandRGB[2] = GL_SRC_COLOR; 256c1f859d4Smrg break; 257c1f859d4Smrg } 258c1f859d4Smrg break; 2597117f1b4Smrg 260c1f859d4Smrg case GL_ADD: 261c1f859d4Smrg mode_rgb = (texBaseFormat == GL_ALPHA) ? GL_REPLACE : GL_ADD; 262c1f859d4Smrg mode_a = (texBaseFormat == GL_INTENSITY) ? GL_ADD : GL_MODULATE; 263c1f859d4Smrg break; 2647117f1b4Smrg 265c1f859d4Smrg default: 266c1f859d4Smrg _mesa_problem(NULL, 26756e89960Smrg "Invalid texture env mode 0x%x in calculate_derived_texenv", 26856e89960Smrg mode); 2697117f1b4Smrg return; 2707117f1b4Smrg } 271c1f859d4Smrg 272c1f859d4Smrg state->ModeRGB = (state->SourceRGB[0] != GL_PREVIOUS) 273c1f859d4Smrg ? mode_rgb : GL_REPLACE; 274c1f859d4Smrg state->ModeA = (state->SourceA[0] != GL_PREVIOUS) 275c1f859d4Smrg ? mode_a : GL_REPLACE; 276c1f859d4Smrg} 2777117f1b4Smrg 2787117f1b4Smrg 2797117f1b4Smrg 2807117f1b4Smrg 2817117f1b4Smrg/* GL_ARB_multitexture */ 2827117f1b4Smrgvoid GLAPIENTRY 2837117f1b4Smrg_mesa_ActiveTextureARB(GLenum texture) 2847117f1b4Smrg{ 2857117f1b4Smrg GET_CURRENT_CONTEXT(ctx); 2867117f1b4Smrg const GLuint texUnit = texture - GL_TEXTURE0; 2877117f1b4Smrg ASSERT_OUTSIDE_BEGIN_END(ctx); 2887117f1b4Smrg 2897117f1b4Smrg if (MESA_VERBOSE & (VERBOSE_API|VERBOSE_TEXTURE)) 2907117f1b4Smrg _mesa_debug(ctx, "glActiveTexture %s\n", 2917117f1b4Smrg _mesa_lookup_enum_by_nr(texture)); 2927117f1b4Smrg 293c1f859d4Smrg if (texUnit >= ctx->Const.MaxTextureImageUnits) { 2947117f1b4Smrg _mesa_error(ctx, GL_INVALID_ENUM, "glActiveTexture(texture)"); 2957117f1b4Smrg return; 2967117f1b4Smrg } 2977117f1b4Smrg 2987117f1b4Smrg if (ctx->Texture.CurrentUnit == texUnit) 2997117f1b4Smrg return; 3007117f1b4Smrg 3017117f1b4Smrg FLUSH_VERTICES(ctx, _NEW_TEXTURE); 3027117f1b4Smrg 3037117f1b4Smrg ctx->Texture.CurrentUnit = texUnit; 3047117f1b4Smrg if (ctx->Transform.MatrixMode == GL_TEXTURE) { 3057117f1b4Smrg /* update current stack pointer */ 3067117f1b4Smrg ctx->CurrentStack = &ctx->TextureMatrixStack[texUnit]; 3077117f1b4Smrg } 3087117f1b4Smrg} 3097117f1b4Smrg 3107117f1b4Smrg 3117117f1b4Smrg/* GL_ARB_multitexture */ 3127117f1b4Smrgvoid GLAPIENTRY 3137117f1b4Smrg_mesa_ClientActiveTextureARB(GLenum texture) 3147117f1b4Smrg{ 3157117f1b4Smrg GET_CURRENT_CONTEXT(ctx); 3167117f1b4Smrg GLuint texUnit = texture - GL_TEXTURE0; 3177117f1b4Smrg ASSERT_OUTSIDE_BEGIN_END(ctx); 3187117f1b4Smrg 31956e89960Smrg if (MESA_VERBOSE & (VERBOSE_API | VERBOSE_TEXTURE)) 32056e89960Smrg _mesa_debug(ctx, "glClientActiveTexture %s\n", 32156e89960Smrg _mesa_lookup_enum_by_nr(texture)); 32256e89960Smrg 3237117f1b4Smrg if (texUnit >= ctx->Const.MaxTextureCoordUnits) { 3247117f1b4Smrg _mesa_error(ctx, GL_INVALID_ENUM, "glClientActiveTexture(texture)"); 3257117f1b4Smrg return; 3267117f1b4Smrg } 3277117f1b4Smrg 32856e89960Smrg if (ctx->Array.ActiveTexture == texUnit) 32956e89960Smrg return; 33056e89960Smrg 3317117f1b4Smrg FLUSH_VERTICES(ctx, _NEW_ARRAY); 3327117f1b4Smrg ctx->Array.ActiveTexture = texUnit; 3337117f1b4Smrg} 3347117f1b4Smrg 3357117f1b4Smrg 3367117f1b4Smrg 3377117f1b4Smrg/**********************************************************************/ 3387117f1b4Smrg/***** State management *****/ 3397117f1b4Smrg/**********************************************************************/ 3407117f1b4Smrg 3417117f1b4Smrg 3427117f1b4Smrg/** 3437117f1b4Smrg * \note This routine refers to derived texture attribute values to 3447117f1b4Smrg * compute the ENABLE_TEXMAT flags, but is only called on 3457117f1b4Smrg * _NEW_TEXTURE_MATRIX. On changes to _NEW_TEXTURE, the ENABLE_TEXMAT 3467117f1b4Smrg * flags are updated by _mesa_update_textures(), below. 3477117f1b4Smrg * 3487117f1b4Smrg * \param ctx GL context. 3497117f1b4Smrg */ 3507117f1b4Smrgstatic void 3517117f1b4Smrgupdate_texture_matrices( GLcontext *ctx ) 3527117f1b4Smrg{ 35356e89960Smrg GLuint u; 3547117f1b4Smrg 35556e89960Smrg ctx->Texture._TexMatEnabled = 0x0; 3567117f1b4Smrg 35756e89960Smrg for (u = 0; u < ctx->Const.MaxTextureCoordUnits; u++) { 35856e89960Smrg if (_math_matrix_is_dirty(ctx->TextureMatrixStack[u].Top)) { 35956e89960Smrg _math_matrix_analyse( ctx->TextureMatrixStack[u].Top ); 3607117f1b4Smrg 36156e89960Smrg if (ctx->Texture.Unit[u]._ReallyEnabled && 36256e89960Smrg ctx->TextureMatrixStack[u].Top->type != MATRIX_IDENTITY) 36356e89960Smrg ctx->Texture._TexMatEnabled |= ENABLE_TEXMAT(u); 3647117f1b4Smrg } 3657117f1b4Smrg } 3667117f1b4Smrg} 3677117f1b4Smrg 3687117f1b4Smrg 369c1f859d4Smrg/** 37056e89960Smrg * Examine texture unit's combine/env state to update derived state. 371c1f859d4Smrg */ 372c1f859d4Smrgstatic void 37356e89960Smrgupdate_tex_combine(GLcontext *ctx, struct gl_texture_unit *texUnit) 374c1f859d4Smrg{ 37556e89960Smrg struct gl_tex_env_combine_state *combine; 37656e89960Smrg 37756e89960Smrg /* Set the texUnit->_CurrentCombine field to point to the user's combiner 37856e89960Smrg * state, or the combiner state which is derived from traditional texenv 37956e89960Smrg * mode. 380c1f859d4Smrg */ 38156e89960Smrg if (texUnit->EnvMode == GL_COMBINE || 38256e89960Smrg texUnit->EnvMode == GL_COMBINE4_NV) { 38356e89960Smrg texUnit->_CurrentCombine = & texUnit->Combine; 384c1f859d4Smrg } 38556e89960Smrg else { 38656e89960Smrg const struct gl_texture_object *texObj = texUnit->_Current; 38756e89960Smrg GLenum format = texObj->Image[0][texObj->BaseLevel]->_BaseFormat; 38856e89960Smrg if (format == GL_COLOR_INDEX) { 38956e89960Smrg format = GL_RGBA; /* a bit of a hack */ 390c1f859d4Smrg } 39156e89960Smrg else if (format == GL_DEPTH_COMPONENT || 39256e89960Smrg format == GL_DEPTH_STENCIL_EXT) { 39356e89960Smrg format = texObj->DepthMode; 394c1f859d4Smrg } 39556e89960Smrg calculate_derived_texenv(&texUnit->_EnvMode, texUnit->EnvMode, format); 39656e89960Smrg texUnit->_CurrentCombine = & texUnit->_EnvMode; 397c1f859d4Smrg } 398c1f859d4Smrg 39956e89960Smrg combine = texUnit->_CurrentCombine; 400c1f859d4Smrg 40156e89960Smrg /* Determine number of source RGB terms in the combiner function */ 40256e89960Smrg switch (combine->ModeRGB) { 40356e89960Smrg case GL_REPLACE: 40456e89960Smrg combine->_NumArgsRGB = 1; 40556e89960Smrg break; 40656e89960Smrg case GL_ADD: 40756e89960Smrg case GL_ADD_SIGNED: 40856e89960Smrg if (texUnit->EnvMode == GL_COMBINE4_NV) 40956e89960Smrg combine->_NumArgsRGB = 4; 41056e89960Smrg else 41156e89960Smrg combine->_NumArgsRGB = 2; 41256e89960Smrg break; 41356e89960Smrg case GL_MODULATE: 41456e89960Smrg case GL_SUBTRACT: 41556e89960Smrg case GL_DOT3_RGB: 41656e89960Smrg case GL_DOT3_RGBA: 41756e89960Smrg case GL_DOT3_RGB_EXT: 41856e89960Smrg case GL_DOT3_RGBA_EXT: 41956e89960Smrg combine->_NumArgsRGB = 2; 42056e89960Smrg break; 42156e89960Smrg case GL_INTERPOLATE: 42256e89960Smrg case GL_MODULATE_ADD_ATI: 42356e89960Smrg case GL_MODULATE_SIGNED_ADD_ATI: 42456e89960Smrg case GL_MODULATE_SUBTRACT_ATI: 42556e89960Smrg combine->_NumArgsRGB = 3; 42656e89960Smrg break; 42756e89960Smrg case GL_BUMP_ENVMAP_ATI: 42856e89960Smrg /* no real arguments for this case */ 42956e89960Smrg combine->_NumArgsRGB = 0; 43056e89960Smrg break; 43156e89960Smrg default: 43256e89960Smrg combine->_NumArgsRGB = 0; 43356e89960Smrg _mesa_problem(ctx, "invalid RGB combine mode in update_texture_state"); 43456e89960Smrg return; 43556e89960Smrg } 43656e89960Smrg 43756e89960Smrg /* Determine number of source Alpha terms in the combiner function */ 43856e89960Smrg switch (combine->ModeA) { 43956e89960Smrg case GL_REPLACE: 44056e89960Smrg combine->_NumArgsA = 1; 44156e89960Smrg break; 44256e89960Smrg case GL_ADD: 44356e89960Smrg case GL_ADD_SIGNED: 44456e89960Smrg if (texUnit->EnvMode == GL_COMBINE4_NV) 44556e89960Smrg combine->_NumArgsA = 4; 44656e89960Smrg else 44756e89960Smrg combine->_NumArgsA = 2; 44856e89960Smrg break; 44956e89960Smrg case GL_MODULATE: 45056e89960Smrg case GL_SUBTRACT: 45156e89960Smrg combine->_NumArgsA = 2; 45256e89960Smrg break; 45356e89960Smrg case GL_INTERPOLATE: 45456e89960Smrg case GL_MODULATE_ADD_ATI: 45556e89960Smrg case GL_MODULATE_SIGNED_ADD_ATI: 45656e89960Smrg case GL_MODULATE_SUBTRACT_ATI: 45756e89960Smrg combine->_NumArgsA = 3; 45856e89960Smrg break; 45956e89960Smrg default: 46056e89960Smrg combine->_NumArgsA = 0; 46156e89960Smrg _mesa_problem(ctx, "invalid Alpha combine mode in update_texture_state"); 46256e89960Smrg break; 4637117f1b4Smrg } 4647117f1b4Smrg} 4657117f1b4Smrg 4667117f1b4Smrg 4677117f1b4Smrg/** 4687117f1b4Smrg * \note This routine refers to derived texture matrix values to 4697117f1b4Smrg * compute the ENABLE_TEXMAT flags, but is only called on 4707117f1b4Smrg * _NEW_TEXTURE. On changes to _NEW_TEXTURE_MATRIX, the ENABLE_TEXMAT 4717117f1b4Smrg * flags are updated by _mesa_update_texture_matrices, above. 4727117f1b4Smrg * 4737117f1b4Smrg * \param ctx GL context. 4747117f1b4Smrg */ 4757117f1b4Smrgstatic void 4767117f1b4Smrgupdate_texture_state( GLcontext *ctx ) 4777117f1b4Smrg{ 4787117f1b4Smrg GLuint unit; 4797117f1b4Smrg struct gl_fragment_program *fprog = NULL; 4807117f1b4Smrg struct gl_vertex_program *vprog = NULL; 48156e89960Smrg GLbitfield enabledFragUnits = 0x0; 4827117f1b4Smrg 4837117f1b4Smrg if (ctx->Shader.CurrentProgram && 4847117f1b4Smrg ctx->Shader.CurrentProgram->LinkStatus) { 4857117f1b4Smrg fprog = ctx->Shader.CurrentProgram->FragmentProgram; 4867117f1b4Smrg vprog = ctx->Shader.CurrentProgram->VertexProgram; 4877117f1b4Smrg } 4887117f1b4Smrg else { 4897117f1b4Smrg if (ctx->FragmentProgram._Enabled) { 4907117f1b4Smrg fprog = ctx->FragmentProgram.Current; 4917117f1b4Smrg } 4927117f1b4Smrg if (ctx->VertexProgram._Enabled) { 4937117f1b4Smrg /* XXX enable this if/when non-shader vertex programs get 4947117f1b4Smrg * texture fetches: 4957117f1b4Smrg vprog = ctx->VertexProgram.Current; 4967117f1b4Smrg */ 4977117f1b4Smrg } 4987117f1b4Smrg } 4997117f1b4Smrg 50056e89960Smrg /* TODO: only set this if there are actual changes */ 50156e89960Smrg ctx->NewState |= _NEW_TEXTURE; 5027117f1b4Smrg 50356e89960Smrg ctx->Texture._EnabledUnits = 0x0; 50456e89960Smrg ctx->Texture._GenFlags = 0x0; 50556e89960Smrg ctx->Texture._TexMatEnabled = 0x0; 50656e89960Smrg ctx->Texture._TexGenEnabled = 0x0; 5077117f1b4Smrg 5087117f1b4Smrg /* 5097117f1b4Smrg * Update texture unit state. 5107117f1b4Smrg */ 511c1f859d4Smrg for (unit = 0; unit < ctx->Const.MaxTextureImageUnits; unit++) { 5127117f1b4Smrg struct gl_texture_unit *texUnit = &ctx->Texture.Unit[unit]; 51356e89960Smrg GLbitfield enabledVertTargets = 0x0; 51456e89960Smrg GLbitfield enabledFragTargets = 0x0; 51556e89960Smrg GLbitfield enabledTargets = 0x0; 51656e89960Smrg GLuint texIndex; 5177117f1b4Smrg 518c1f859d4Smrg /* Get the bitmask of texture target enables. 5197117f1b4Smrg * enableBits will be a mask of the TEXTURE_*_BIT flags indicating 5207117f1b4Smrg * which texture targets are enabled (fixed function) or referenced 5217117f1b4Smrg * by a fragment shader/program. When multiple flags are set, we'll 52256e89960Smrg * settle on the one with highest priority (see below). 5237117f1b4Smrg */ 524c1f859d4Smrg if (vprog) { 52556e89960Smrg enabledVertTargets |= vprog->Base.TexturesUsed[unit]; 526c1f859d4Smrg } 52756e89960Smrg 528c1f859d4Smrg if (fprog) { 52956e89960Smrg enabledFragTargets |= fprog->Base.TexturesUsed[unit]; 5307117f1b4Smrg } 5317117f1b4Smrg else { 532c1f859d4Smrg /* fixed-function fragment program */ 53356e89960Smrg enabledFragTargets |= texUnit->Enabled; 534c1f859d4Smrg } 535c1f859d4Smrg 53656e89960Smrg enabledTargets = enabledVertTargets | enabledFragTargets; 537c1f859d4Smrg 53856e89960Smrg texUnit->_ReallyEnabled = 0x0; 53956e89960Smrg 54056e89960Smrg if (enabledTargets == 0x0) { 54156e89960Smrg /* neither vertex nor fragment processing uses this unit */ 54256e89960Smrg continue; 5437117f1b4Smrg } 5447117f1b4Smrg 54556e89960Smrg /* Look for the highest priority texture target that's enabled (or used 54656e89960Smrg * by the vert/frag shaders) and "complete". That's the one we'll use 54756e89960Smrg * for texturing. If we're using vert/frag program we're guaranteed 54856e89960Smrg * that bitcount(enabledBits) <= 1. 54956e89960Smrg * Note that the TEXTURE_x_INDEX values are in high to low priority. 5507117f1b4Smrg */ 55156e89960Smrg for (texIndex = 0; texIndex < NUM_TEXTURE_TARGETS; texIndex++) { 55256e89960Smrg if (enabledTargets & (1 << texIndex)) { 55356e89960Smrg struct gl_texture_object *texObj = texUnit->CurrentTex[texIndex]; 55456e89960Smrg if (!texObj->_Complete) { 55556e89960Smrg _mesa_test_texobj_completeness(ctx, texObj); 55656e89960Smrg } 55756e89960Smrg if (texObj->_Complete) { 55856e89960Smrg texUnit->_ReallyEnabled = 1 << texIndex; 55956e89960Smrg _mesa_reference_texobj(&texUnit->_Current, texObj); 56056e89960Smrg break; 56156e89960Smrg } 56256e89960Smrg } 563c1f859d4Smrg } 5647117f1b4Smrg 5657117f1b4Smrg if (!texUnit->_ReallyEnabled) { 56656e89960Smrg if (fprog) { 56756e89960Smrg /* If we get here it means the shader is expecting a texture 56856e89960Smrg * object, but there isn't one (or it's incomplete). Use the 56956e89960Smrg * fallback texture. 57056e89960Smrg */ 57156e89960Smrg struct gl_texture_object *texObj = _mesa_get_fallback_texture(ctx); 57256e89960Smrg texUnit->_ReallyEnabled = 1 << TEXTURE_2D_INDEX; 57356e89960Smrg _mesa_reference_texobj(&texUnit->_Current, texObj); 5747117f1b4Smrg } 57556e89960Smrg else { 57656e89960Smrg /* fixed-function: texture unit is really disabled */ 57756e89960Smrg continue; 5787117f1b4Smrg } 5797117f1b4Smrg } 5807117f1b4Smrg 58156e89960Smrg /* if we get here, we know this texture unit is enabled */ 5827117f1b4Smrg 58356e89960Smrg ctx->Texture._EnabledUnits |= (1 << unit); 58456e89960Smrg 58556e89960Smrg if (enabledFragTargets) 58656e89960Smrg enabledFragUnits |= (1 << unit); 58756e89960Smrg 58856e89960Smrg update_tex_combine(ctx, texUnit); 589c1f859d4Smrg } 590c1f859d4Smrg 59156e89960Smrg 592c1f859d4Smrg /* Determine which texture coordinate sets are actually needed */ 593c1f859d4Smrg if (fprog) { 594c1f859d4Smrg const GLuint coordMask = (1 << MAX_TEXTURE_COORD_UNITS) - 1; 595c1f859d4Smrg ctx->Texture._EnabledCoordUnits 596c1f859d4Smrg = (fprog->Base.InputsRead >> FRAG_ATTRIB_TEX0) & coordMask; 597c1f859d4Smrg } 598c1f859d4Smrg else { 59956e89960Smrg ctx->Texture._EnabledCoordUnits = enabledFragUnits; 600c1f859d4Smrg } 601c1f859d4Smrg 602c1f859d4Smrg /* Setup texgen for those texture coordinate sets that are in use */ 603c1f859d4Smrg for (unit = 0; unit < ctx->Const.MaxTextureCoordUnits; unit++) { 604c1f859d4Smrg struct gl_texture_unit *texUnit = &ctx->Texture.Unit[unit]; 605c1f859d4Smrg 60656e89960Smrg texUnit->_GenFlags = 0x0; 60756e89960Smrg 608c1f859d4Smrg if (!(ctx->Texture._EnabledCoordUnits & (1 << unit))) 609c1f859d4Smrg continue; 6107117f1b4Smrg 6117117f1b4Smrg if (texUnit->TexGenEnabled) { 6127117f1b4Smrg if (texUnit->TexGenEnabled & S_BIT) { 61356e89960Smrg texUnit->_GenFlags |= texUnit->GenS._ModeBit; 6147117f1b4Smrg } 6157117f1b4Smrg if (texUnit->TexGenEnabled & T_BIT) { 61656e89960Smrg texUnit->_GenFlags |= texUnit->GenT._ModeBit; 6177117f1b4Smrg } 6187117f1b4Smrg if (texUnit->TexGenEnabled & R_BIT) { 61956e89960Smrg texUnit->_GenFlags |= texUnit->GenR._ModeBit; 62056e89960Smrg } 62156e89960Smrg if (texUnit->TexGenEnabled & Q_BIT) { 62256e89960Smrg texUnit->_GenFlags |= texUnit->GenQ._ModeBit; 6237117f1b4Smrg } 6247117f1b4Smrg 6257117f1b4Smrg ctx->Texture._TexGenEnabled |= ENABLE_TEXGEN(unit); 6267117f1b4Smrg ctx->Texture._GenFlags |= texUnit->_GenFlags; 6277117f1b4Smrg } 6287117f1b4Smrg 6297117f1b4Smrg if (ctx->TextureMatrixStack[unit].Top->type != MATRIX_IDENTITY) 6307117f1b4Smrg ctx->Texture._TexMatEnabled |= ENABLE_TEXMAT(unit); 6317117f1b4Smrg } 6327117f1b4Smrg} 6337117f1b4Smrg 6347117f1b4Smrg 6357117f1b4Smrg/** 6367117f1b4Smrg * Update texture-related derived state. 6377117f1b4Smrg */ 6387117f1b4Smrgvoid 6397117f1b4Smrg_mesa_update_texture( GLcontext *ctx, GLuint new_state ) 6407117f1b4Smrg{ 6417117f1b4Smrg if (new_state & _NEW_TEXTURE_MATRIX) 6427117f1b4Smrg update_texture_matrices( ctx ); 6437117f1b4Smrg 6447117f1b4Smrg if (new_state & (_NEW_TEXTURE | _NEW_PROGRAM)) 6457117f1b4Smrg update_texture_state( ctx ); 6467117f1b4Smrg} 6477117f1b4Smrg 6487117f1b4Smrg 6497117f1b4Smrg/**********************************************************************/ 6507117f1b4Smrg/***** Initialization *****/ 6517117f1b4Smrg/**********************************************************************/ 6527117f1b4Smrg 6537117f1b4Smrg/** 6547117f1b4Smrg * Allocate the proxy textures for the given context. 6557117f1b4Smrg * 6567117f1b4Smrg * \param ctx the context to allocate proxies for. 6577117f1b4Smrg * 6587117f1b4Smrg * \return GL_TRUE on success, or GL_FALSE on failure 6597117f1b4Smrg * 6607117f1b4Smrg * If run out of memory part way through the allocations, clean up and return 6617117f1b4Smrg * GL_FALSE. 6627117f1b4Smrg */ 6637117f1b4Smrgstatic GLboolean 6647117f1b4Smrgalloc_proxy_textures( GLcontext *ctx ) 6657117f1b4Smrg{ 666c1f859d4Smrg static const GLenum targets[] = { 667c1f859d4Smrg GL_TEXTURE_1D, 668c1f859d4Smrg GL_TEXTURE_2D, 669c1f859d4Smrg GL_TEXTURE_3D, 670c1f859d4Smrg GL_TEXTURE_CUBE_MAP_ARB, 671c1f859d4Smrg GL_TEXTURE_RECTANGLE_NV, 672c1f859d4Smrg GL_TEXTURE_1D_ARRAY_EXT, 673c1f859d4Smrg GL_TEXTURE_2D_ARRAY_EXT 674c1f859d4Smrg }; 675c1f859d4Smrg GLint tgt; 6767117f1b4Smrg 677c1f859d4Smrg ASSERT(Elements(targets) == NUM_TEXTURE_TARGETS); 6787117f1b4Smrg 679c1f859d4Smrg for (tgt = 0; tgt < NUM_TEXTURE_TARGETS; tgt++) { 680c1f859d4Smrg if (!(ctx->Texture.ProxyTex[tgt] 681c1f859d4Smrg = ctx->Driver.NewTextureObject(ctx, 0, targets[tgt]))) { 682c1f859d4Smrg /* out of memory, free what we did allocate */ 683c1f859d4Smrg while (--tgt >= 0) { 684c1f859d4Smrg ctx->Driver.DeleteTexture(ctx, ctx->Texture.ProxyTex[tgt]); 685c1f859d4Smrg } 686c1f859d4Smrg return GL_FALSE; 687c1f859d4Smrg } 688c1f859d4Smrg } 6897117f1b4Smrg 690c1f859d4Smrg assert(ctx->Texture.ProxyTex[0]->RefCount == 1); /* sanity check */ 6917117f1b4Smrg return GL_TRUE; 6927117f1b4Smrg} 6937117f1b4Smrg 6947117f1b4Smrg 6957117f1b4Smrg/** 6967117f1b4Smrg * Initialize a texture unit. 6977117f1b4Smrg * 6987117f1b4Smrg * \param ctx GL context. 6997117f1b4Smrg * \param unit texture unit number to be initialized. 7007117f1b4Smrg */ 7017117f1b4Smrgstatic void 7027117f1b4Smrginit_texture_unit( GLcontext *ctx, GLuint unit ) 7037117f1b4Smrg{ 7047117f1b4Smrg struct gl_texture_unit *texUnit = &ctx->Texture.Unit[unit]; 705c1f859d4Smrg GLuint tex; 7067117f1b4Smrg 7077117f1b4Smrg texUnit->EnvMode = GL_MODULATE; 7087117f1b4Smrg ASSIGN_4V( texUnit->EnvColor, 0.0, 0.0, 0.0, 0.0 ); 7097117f1b4Smrg 7107117f1b4Smrg texUnit->Combine = default_combine_state; 7117117f1b4Smrg texUnit->_EnvMode = default_combine_state; 7127117f1b4Smrg texUnit->_CurrentCombine = & texUnit->_EnvMode; 71356e89960Smrg texUnit->BumpTarget = GL_TEXTURE0; 71456e89960Smrg 71556e89960Smrg texUnit->TexGenEnabled = 0x0; 71656e89960Smrg texUnit->GenS.Mode = GL_EYE_LINEAR; 71756e89960Smrg texUnit->GenT.Mode = GL_EYE_LINEAR; 71856e89960Smrg texUnit->GenR.Mode = GL_EYE_LINEAR; 71956e89960Smrg texUnit->GenQ.Mode = GL_EYE_LINEAR; 72056e89960Smrg texUnit->GenS._ModeBit = TEXGEN_EYE_LINEAR; 72156e89960Smrg texUnit->GenT._ModeBit = TEXGEN_EYE_LINEAR; 72256e89960Smrg texUnit->GenR._ModeBit = TEXGEN_EYE_LINEAR; 72356e89960Smrg texUnit->GenQ._ModeBit = TEXGEN_EYE_LINEAR; 7247117f1b4Smrg 7257117f1b4Smrg /* Yes, these plane coefficients are correct! */ 72656e89960Smrg ASSIGN_4V( texUnit->GenS.ObjectPlane, 1.0, 0.0, 0.0, 0.0 ); 72756e89960Smrg ASSIGN_4V( texUnit->GenT.ObjectPlane, 0.0, 1.0, 0.0, 0.0 ); 72856e89960Smrg ASSIGN_4V( texUnit->GenR.ObjectPlane, 0.0, 0.0, 0.0, 0.0 ); 72956e89960Smrg ASSIGN_4V( texUnit->GenQ.ObjectPlane, 0.0, 0.0, 0.0, 0.0 ); 73056e89960Smrg ASSIGN_4V( texUnit->GenS.EyePlane, 1.0, 0.0, 0.0, 0.0 ); 73156e89960Smrg ASSIGN_4V( texUnit->GenT.EyePlane, 0.0, 1.0, 0.0, 0.0 ); 73256e89960Smrg ASSIGN_4V( texUnit->GenR.EyePlane, 0.0, 0.0, 0.0, 0.0 ); 73356e89960Smrg ASSIGN_4V( texUnit->GenQ.EyePlane, 0.0, 0.0, 0.0, 0.0 ); 73456e89960Smrg 73556e89960Smrg /* no mention of this in spec, but maybe id matrix expected? */ 73656e89960Smrg ASSIGN_4V( texUnit->RotMatrix, 1.0, 0.0, 0.0, 1.0 ); 7377117f1b4Smrg 7387117f1b4Smrg /* initialize current texture object ptrs to the shared default objects */ 739c1f859d4Smrg for (tex = 0; tex < NUM_TEXTURE_TARGETS; tex++) { 740c1f859d4Smrg _mesa_reference_texobj(&texUnit->CurrentTex[tex], 741c1f859d4Smrg ctx->Shared->DefaultTex[tex]); 742c1f859d4Smrg } 7437117f1b4Smrg} 7447117f1b4Smrg 7457117f1b4Smrg 7467117f1b4Smrg/** 7477117f1b4Smrg * Initialize texture state for the given context. 7487117f1b4Smrg */ 7497117f1b4SmrgGLboolean 7507117f1b4Smrg_mesa_init_texture(GLcontext *ctx) 7517117f1b4Smrg{ 75256e89960Smrg GLuint u; 7537117f1b4Smrg 7547117f1b4Smrg /* Texture group */ 7557117f1b4Smrg ctx->Texture.CurrentUnit = 0; /* multitexture */ 75656e89960Smrg ctx->Texture._EnabledUnits = 0x0; 7577117f1b4Smrg ctx->Texture.SharedPalette = GL_FALSE; 7587117f1b4Smrg _mesa_init_colortable(&ctx->Texture.Palette); 7597117f1b4Smrg 76056e89960Smrg for (u = 0; u < MAX_TEXTURE_UNITS; u++) 76156e89960Smrg init_texture_unit(ctx, u); 7627117f1b4Smrg 7637117f1b4Smrg /* After we're done initializing the context's texture state the default 7647117f1b4Smrg * texture objects' refcounts should be at least MAX_TEXTURE_UNITS + 1. 7657117f1b4Smrg */ 766c1f859d4Smrg assert(ctx->Shared->DefaultTex[TEXTURE_1D_INDEX]->RefCount 767c1f859d4Smrg >= MAX_TEXTURE_UNITS + 1); 7687117f1b4Smrg 7697117f1b4Smrg /* Allocate proxy textures */ 7707117f1b4Smrg if (!alloc_proxy_textures( ctx )) 7717117f1b4Smrg return GL_FALSE; 7727117f1b4Smrg 7737117f1b4Smrg return GL_TRUE; 7747117f1b4Smrg} 7757117f1b4Smrg 7767117f1b4Smrg 7777117f1b4Smrg/** 778c1f859d4Smrg * Free dynamically-allocted texture data attached to the given context. 7797117f1b4Smrg */ 7807117f1b4Smrgvoid 7817117f1b4Smrg_mesa_free_texture_data(GLcontext *ctx) 7827117f1b4Smrg{ 783c1f859d4Smrg GLuint u, tgt; 7847117f1b4Smrg 7857117f1b4Smrg /* unreference current textures */ 7867117f1b4Smrg for (u = 0; u < MAX_TEXTURE_IMAGE_UNITS; u++) { 787c1f859d4Smrg /* The _Current texture could account for another reference */ 788c1f859d4Smrg _mesa_reference_texobj(&ctx->Texture.Unit[u]._Current, NULL); 789c1f859d4Smrg 790c1f859d4Smrg for (tgt = 0; tgt < NUM_TEXTURE_TARGETS; tgt++) { 79156e89960Smrg _mesa_reference_texobj(&ctx->Texture.Unit[u].CurrentTex[tgt], NULL); 792c1f859d4Smrg } 7937117f1b4Smrg } 7947117f1b4Smrg 7957117f1b4Smrg /* Free proxy texture objects */ 796c1f859d4Smrg for (tgt = 0; tgt < NUM_TEXTURE_TARGETS; tgt++) 797c1f859d4Smrg ctx->Driver.DeleteTexture(ctx, ctx->Texture.ProxyTex[tgt]); 798c1f859d4Smrg 79956e89960Smrg for (u = 0; u < MAX_TEXTURE_IMAGE_UNITS; u++) 80056e89960Smrg _mesa_free_colortable_data(&ctx->Texture.Unit[u].ColorTable); 801c1f859d4Smrg} 802c1f859d4Smrg 8037117f1b4Smrg 804c1f859d4Smrg/** 805c1f859d4Smrg * Update the default texture objects in the given context to reference those 806c1f859d4Smrg * specified in the shared state and release those referencing the old 807c1f859d4Smrg * shared state. 808c1f859d4Smrg */ 809c1f859d4Smrgvoid 810c1f859d4Smrg_mesa_update_default_objects_texture(GLcontext *ctx) 811c1f859d4Smrg{ 81256e89960Smrg GLuint u, tex; 8137117f1b4Smrg 81456e89960Smrg for (u = 0; u < MAX_TEXTURE_UNITS; u++) { 81556e89960Smrg struct gl_texture_unit *texUnit = &ctx->Texture.Unit[u]; 816c1f859d4Smrg for (tex = 0; tex < NUM_TEXTURE_TARGETS; tex++) { 817c1f859d4Smrg _mesa_reference_texobj(&texUnit->CurrentTex[tex], 818c1f859d4Smrg ctx->Shared->DefaultTex[tex]); 819c1f859d4Smrg } 820c1f859d4Smrg } 8217117f1b4Smrg} 822