prog_statevars.c revision a2786a97d74647662f1fe6aa29257e70b9e3636a
100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian/*
200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * Mesa 3-D graphics library
300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * Version:  6.5.3
400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian *
5b7978af6936d186112727cb9858fe7740eef1a7cBrian * Copyright (C) 1999-2007  Brian Paul   All Rights Reserved.
600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian *
700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * Permission is hereby granted, free of charge, to any person obtaining a
800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * copy of this software and associated documentation files (the "Software"),
900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * to deal in the Software without restriction, including without limitation
1000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * the rights to use, copy, modify, merge, publish, distribute, sublicense,
1100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * and/or sell copies of the Software, and to permit persons to whom the
1200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * Software is furnished to do so, subject to the following conditions:
1300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian *
1400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * The above copyright notice and this permission notice shall be included
1500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * in all copies or substantial portions of the Software.
1600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian *
1700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
1800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
1900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
2000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
2100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
2200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
2300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian */
2400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
2500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian/**
2600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * \file prog_statevars.c
2700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * Program state variable management.
2800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * \author Brian Paul
2900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian */
3000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
3100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
3200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian#include "glheader.h"
3300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian#include "context.h"
3400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian#include "hash.h"
3500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian#include "imports.h"
3600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian#include "macros.h"
3700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian#include "mtypes.h"
3800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian#include "prog_statevars.h"
3900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian#include "prog_parameter.h"
4000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian#include "nvvertparse.h"
4100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
4200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
4300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian/**
4400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * Use the list of tokens in the state[] array to find global GL state
4500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * and return it in <value>.  Usually, four values are returned in <value>
4600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * but matrix queries may return as many as 16 values.
4700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * This function is used for ARB vertex/fragment programs.
4800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * The program parser will produce the state[] values.
4900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian */
5000cdc0a472c55330cbc58317f01b07f8f90be5a5Brianstatic void
5100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian_mesa_fetch_state(GLcontext *ctx, const gl_state_index state[],
5200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian                  GLfloat *value)
5300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian{
5400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   switch (state[0]) {
5500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_MATERIAL:
5600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      {
5700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[1] is either 0=front or 1=back side */
5800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         const GLuint face = (GLuint) state[1];
5900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         const struct gl_material *mat = &ctx->Light.Material;
6000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         ASSERT(face == 0 || face == 1);
6100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* we rely on tokens numbered so that _BACK_ == _FRONT_+ 1 */
6200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         ASSERT(MAT_ATTRIB_FRONT_AMBIENT + 1 == MAT_ATTRIB_BACK_AMBIENT);
6300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* XXX we could get rid of this switch entirely with a little
6400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian          * work in arbprogparse.c's parse_state_single_item().
6500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian          */
6600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[2] is the material attribute */
6700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         switch (state[2]) {
6800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_AMBIENT:
6900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, mat->Attrib[MAT_ATTRIB_FRONT_AMBIENT + face]);
7000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
7100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_DIFFUSE:
7200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, mat->Attrib[MAT_ATTRIB_FRONT_DIFFUSE + face]);
7300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
7400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_SPECULAR:
7500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, mat->Attrib[MAT_ATTRIB_FRONT_SPECULAR + face]);
7600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
7700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_EMISSION:
7800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, mat->Attrib[MAT_ATTRIB_FRONT_EMISSION + face]);
7900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
8000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_SHININESS:
8100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            value[0] = mat->Attrib[MAT_ATTRIB_FRONT_SHININESS + face][0];
8200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            value[1] = 0.0F;
8300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            value[2] = 0.0F;
8400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            value[3] = 1.0F;
8500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
8600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         default:
8700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            _mesa_problem(ctx, "Invalid material state in fetch_state");
8800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
8900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
9000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
9100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHT:
9200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      {
9300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[1] is the light number */
9400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         const GLuint ln = (GLuint) state[1];
9500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[2] is the light attribute */
9600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         switch (state[2]) {
9700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_AMBIENT:
9800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Light.Light[ln].Ambient);
9900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
10000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_DIFFUSE:
10100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Light.Light[ln].Diffuse);
10200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
10300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_SPECULAR:
10400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Light.Light[ln].Specular);
10500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
10600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_POSITION:
10700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Light.Light[ln].EyePosition);
10800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
10900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_ATTENUATION:
11000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            value[0] = ctx->Light.Light[ln].ConstantAttenuation;
11100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            value[1] = ctx->Light.Light[ln].LinearAttenuation;
11200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            value[2] = ctx->Light.Light[ln].QuadraticAttenuation;
11300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            value[3] = ctx->Light.Light[ln].SpotExponent;
11400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
11500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_SPOT_DIRECTION:
11600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_3V(value, ctx->Light.Light[ln].EyeDirection);
11700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            value[3] = ctx->Light.Light[ln]._CosCutoff;
11800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
119f958aabdf3e3dc82827628cab97b159bd5089651Brian         case STATE_SPOT_CUTOFF:
120f958aabdf3e3dc82827628cab97b159bd5089651Brian            value[0] = ctx->Light.Light[ln].SpotCutoff;
121f958aabdf3e3dc82827628cab97b159bd5089651Brian            return;
122f958aabdf3e3dc82827628cab97b159bd5089651Brian         case STATE_HALF_VECTOR:
12300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            {
12400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               GLfloat eye_z[] = {0, 0, 1};
12500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
12600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               /* Compute infinite half angle vector:
12700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian                *   half-vector = light_position + (0, 0, 1)
12800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian                * and then normalize.  w = 0
12900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian		*
13000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian		* light.EyePosition.w should be 0 for infinite lights.
13100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian                */
13200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	       ADD_3V(value, eye_z, ctx->Light.Light[ln].EyePosition);
13300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	       NORMALIZE_3FV(value);
13400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	       value[3] = 0;
13500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            }
13600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
13700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	 case STATE_POSITION_NORMALIZED:
13800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Light.Light[ln].EyePosition);
13900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	    NORMALIZE_3FV( value );
14000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
14100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         default:
14200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            _mesa_problem(ctx, "Invalid light state in fetch_state");
14300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
14400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
14500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
14600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHTMODEL_AMBIENT:
14700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      COPY_4V(value, ctx->Light.Model.Ambient);
14800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
14900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHTMODEL_SCENECOLOR:
15000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      if (state[1] == 0) {
15100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* front */
15200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         GLint i;
15300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         for (i = 0; i < 3; i++) {
15400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            value[i] = ctx->Light.Model.Ambient[i]
15500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               * ctx->Light.Material.Attrib[MAT_ATTRIB_FRONT_AMBIENT][i]
15600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               + ctx->Light.Material.Attrib[MAT_ATTRIB_FRONT_EMISSION][i];
15700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
15800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	 value[3] = ctx->Light.Material.Attrib[MAT_ATTRIB_FRONT_DIFFUSE][3];
15900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
16000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      else {
16100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* back */
16200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         GLint i;
16300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         for (i = 0; i < 3; i++) {
16400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            value[i] = ctx->Light.Model.Ambient[i]
16500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               * ctx->Light.Material.Attrib[MAT_ATTRIB_BACK_AMBIENT][i]
16600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               + ctx->Light.Material.Attrib[MAT_ATTRIB_BACK_EMISSION][i];
16700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
16800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	 value[3] = ctx->Light.Material.Attrib[MAT_ATTRIB_BACK_DIFFUSE][3];
16900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
17000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
17100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHTPROD:
17200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      {
17300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         const GLuint ln = (GLuint) state[1];
17400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         const GLuint face = (GLuint) state[2];
17500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         GLint i;
17600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         ASSERT(face == 0 || face == 1);
17700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         switch (state[3]) {
17800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            case STATE_AMBIENT:
17900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               for (i = 0; i < 3; i++) {
18000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian                  value[i] = ctx->Light.Light[ln].Ambient[i] *
18100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian                     ctx->Light.Material.Attrib[MAT_ATTRIB_FRONT_AMBIENT+face][i];
18200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               }
18300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               /* [3] = material alpha */
18400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               value[3] = ctx->Light.Material.Attrib[MAT_ATTRIB_FRONT_DIFFUSE+face][3];
18500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               return;
18600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            case STATE_DIFFUSE:
18700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               for (i = 0; i < 3; i++) {
18800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian                  value[i] = ctx->Light.Light[ln].Diffuse[i] *
18900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian                     ctx->Light.Material.Attrib[MAT_ATTRIB_FRONT_DIFFUSE+face][i];
19000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               }
19100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               /* [3] = material alpha */
19200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               value[3] = ctx->Light.Material.Attrib[MAT_ATTRIB_FRONT_DIFFUSE+face][3];
19300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               return;
19400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            case STATE_SPECULAR:
19500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               for (i = 0; i < 3; i++) {
19600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian                  value[i] = ctx->Light.Light[ln].Specular[i] *
19700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian                     ctx->Light.Material.Attrib[MAT_ATTRIB_FRONT_SPECULAR+face][i];
19800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               }
19900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               /* [3] = material alpha */
20000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               value[3] = ctx->Light.Material.Attrib[MAT_ATTRIB_FRONT_DIFFUSE+face][3];
20100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               return;
20200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            default:
20300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               _mesa_problem(ctx, "Invalid lightprod state in fetch_state");
20400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               return;
20500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
20600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
20700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXGEN:
20800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      {
20900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[1] is the texture unit */
21000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         const GLuint unit = (GLuint) state[1];
21100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[2] is the texgen attribute */
21200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         switch (state[2]) {
21300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_TEXGEN_EYE_S:
21400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Texture.Unit[unit].EyePlaneS);
21500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
21600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_TEXGEN_EYE_T:
21700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Texture.Unit[unit].EyePlaneT);
21800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
21900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_TEXGEN_EYE_R:
22000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Texture.Unit[unit].EyePlaneR);
22100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
22200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_TEXGEN_EYE_Q:
22300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Texture.Unit[unit].EyePlaneQ);
22400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
22500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_TEXGEN_OBJECT_S:
22600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Texture.Unit[unit].ObjectPlaneS);
22700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
22800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_TEXGEN_OBJECT_T:
22900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Texture.Unit[unit].ObjectPlaneT);
23000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
23100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_TEXGEN_OBJECT_R:
23200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Texture.Unit[unit].ObjectPlaneR);
23300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
23400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         case STATE_TEXGEN_OBJECT_Q:
23500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            COPY_4V(value, ctx->Texture.Unit[unit].ObjectPlaneQ);
23600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
23700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         default:
23800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            _mesa_problem(ctx, "Invalid texgen state in fetch_state");
23900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
24000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
24100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
24200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXENV_COLOR:
24300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      {
24400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[1] is the texture unit */
24500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         const GLuint unit = (GLuint) state[1];
24600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         COPY_4V(value, ctx->Texture.Unit[unit].EnvColor);
24700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
24800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
249776bc9cf55b116e17dddde4d097985b51879c83fBrian   case STATE_FOG_COLOR:
250776bc9cf55b116e17dddde4d097985b51879c83fBrian      COPY_4V(value, ctx->Fog.Color);
251776bc9cf55b116e17dddde4d097985b51879c83fBrian      return;
252776bc9cf55b116e17dddde4d097985b51879c83fBrian   case STATE_FOG_PARAMS:
253776bc9cf55b116e17dddde4d097985b51879c83fBrian      value[0] = ctx->Fog.Density;
254776bc9cf55b116e17dddde4d097985b51879c83fBrian      value[1] = ctx->Fog.Start;
255776bc9cf55b116e17dddde4d097985b51879c83fBrian      value[2] = ctx->Fog.End;
256776bc9cf55b116e17dddde4d097985b51879c83fBrian      value[3] = 1.0F / (ctx->Fog.End - ctx->Fog.Start);
25700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
25800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_CLIPPLANE:
25900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      {
26000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         const GLuint plane = (GLuint) state[1];
26100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         COPY_4V(value, ctx->Transform.EyeUserPlane[plane]);
26200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
26300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
264776bc9cf55b116e17dddde4d097985b51879c83fBrian   case STATE_POINT_SIZE:
265776bc9cf55b116e17dddde4d097985b51879c83fBrian      value[0] = ctx->Point.Size;
266776bc9cf55b116e17dddde4d097985b51879c83fBrian      value[1] = ctx->Point.MinSize;
267776bc9cf55b116e17dddde4d097985b51879c83fBrian      value[2] = ctx->Point.MaxSize;
268776bc9cf55b116e17dddde4d097985b51879c83fBrian      value[3] = ctx->Point.Threshold;
269776bc9cf55b116e17dddde4d097985b51879c83fBrian      return;
270776bc9cf55b116e17dddde4d097985b51879c83fBrian   case STATE_POINT_ATTENUATION:
271776bc9cf55b116e17dddde4d097985b51879c83fBrian      value[0] = ctx->Point.Params[0];
272776bc9cf55b116e17dddde4d097985b51879c83fBrian      value[1] = ctx->Point.Params[1];
273776bc9cf55b116e17dddde4d097985b51879c83fBrian      value[2] = ctx->Point.Params[2];
274776bc9cf55b116e17dddde4d097985b51879c83fBrian      value[3] = 1.0F;
27500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
2766531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_MODELVIEW_MATRIX:
2776531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_PROJECTION_MATRIX:
2786531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_MVP_MATRIX:
2796531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_TEXTURE_MATRIX:
2806531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_PROGRAM_MATRIX:
2816531952b3c979be0dc95704beb3c3b9dad1dc37bBrian      /*case STATE_MATRIX:*/
28200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      {
28300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[1] = modelview, projection, texture, etc. */
28400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[2] = which texture matrix or program matrix */
28500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[3] = first row to fetch */
28600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[4] = last row to fetch */
28700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[5] = transpose, inverse or invtrans */
28800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
28900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         const GLmatrix *matrix;
2906531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         const gl_state_index mat = state[0];
2916531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         const GLuint index = (GLuint) state[1];
2926531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         const GLuint firstRow = (GLuint) state[2];
2936531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         const GLuint lastRow = (GLuint) state[3];
2946531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         const gl_state_index modifier = state[4];
29500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         const GLfloat *m;
29600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         GLuint row, i;
2976531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         ASSERT(firstRow >= 0);
2986531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         ASSERT(firstRow < 4);
2996531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         ASSERT(lastRow >= 0);
3006531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         ASSERT(lastRow < 4);
3016531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         if (mat == STATE_MODELVIEW_MATRIX) {
30200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            matrix = ctx->ModelviewMatrixStack.Top;
30300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
3046531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         else if (mat == STATE_PROJECTION_MATRIX) {
30500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            matrix = ctx->ProjectionMatrixStack.Top;
30600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
3076531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         else if (mat == STATE_MVP_MATRIX) {
30800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            matrix = &ctx->_ModelProjectMatrix;
30900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
3106531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         else if (mat == STATE_TEXTURE_MATRIX) {
31100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            matrix = ctx->TextureMatrixStack[index].Top;
31200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
3136531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         else if (mat == STATE_PROGRAM_MATRIX) {
31400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            matrix = ctx->ProgramMatrixStack[index].Top;
31500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
31600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         else {
31700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            _mesa_problem(ctx, "Bad matrix name in _mesa_fetch_state()");
31800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            return;
31900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
32000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         if (modifier == STATE_MATRIX_INVERSE ||
32100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian             modifier == STATE_MATRIX_INVTRANS) {
32200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            /* Be sure inverse is up to date:
32300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	     */
32400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            _math_matrix_alloc_inv( (GLmatrix *) matrix );
32500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	    _math_matrix_analyse( (GLmatrix*) matrix );
32600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            m = matrix->inv;
32700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
32800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         else {
32900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            m = matrix->m;
33000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
33100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         if (modifier == STATE_MATRIX_TRANSPOSE ||
33200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian             modifier == STATE_MATRIX_INVTRANS) {
33300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            for (i = 0, row = firstRow; row <= lastRow; row++) {
33400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               value[i++] = m[row * 4 + 0];
33500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               value[i++] = m[row * 4 + 1];
33600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               value[i++] = m[row * 4 + 2];
33700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               value[i++] = m[row * 4 + 3];
33800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            }
33900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
34000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         else {
34100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            for (i = 0, row = firstRow; row <= lastRow; row++) {
34200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               value[i++] = m[row + 0];
34300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               value[i++] = m[row + 4];
34400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               value[i++] = m[row + 8];
34500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               value[i++] = m[row + 12];
34600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            }
34700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
34800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
34900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
35000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_DEPTH_RANGE:
35100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      value[0] = ctx->Viewport.Near;                     /* near       */
35200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      value[1] = ctx->Viewport.Far;                      /* far        */
35300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      value[2] = ctx->Viewport.Far - ctx->Viewport.Near; /* far - near */
35400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      value[3] = 0;
35500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
35600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_FRAGMENT_PROGRAM:
35700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      {
35800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[1] = {STATE_ENV, STATE_LOCAL} */
35900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[2] = parameter index          */
36000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         const int idx = (int) state[2];
36100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         switch (state[1]) {
36200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            case STATE_ENV:
36300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               COPY_4V(value, ctx->FragmentProgram.Parameters[idx]);
36400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               break;
36500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            case STATE_LOCAL:
36600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               COPY_4V(value, ctx->FragmentProgram.Current->Base.LocalParams[idx]);
36700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               break;
36800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            default:
36900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               _mesa_problem(ctx, "Bad state switch in _mesa_fetch_state()");
37000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               return;
37100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
37200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
37300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
37400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
37500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_VERTEX_PROGRAM:
37600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      {
37700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[1] = {STATE_ENV, STATE_LOCAL} */
37800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* state[2] = parameter index          */
37900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         const int idx = (int) state[2];
38000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         switch (state[1]) {
38100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            case STATE_ENV:
38200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               COPY_4V(value, ctx->VertexProgram.Parameters[idx]);
38300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               break;
38400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            case STATE_LOCAL:
38500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               COPY_4V(value, ctx->VertexProgram.Current->Base.LocalParams[idx]);
38600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               break;
38700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            default:
38800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               _mesa_problem(ctx, "Bad state switch in _mesa_fetch_state()");
38900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               return;
39000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
39100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
39200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
39300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
394f958aabdf3e3dc82827628cab97b159bd5089651Brian   case STATE_NORMAL_SCALE:
395f958aabdf3e3dc82827628cab97b159bd5089651Brian      ASSIGN_4V(value, ctx->_ModelViewInvScale, 0, 0, 1);
396f958aabdf3e3dc82827628cab97b159bd5089651Brian      return;
397f958aabdf3e3dc82827628cab97b159bd5089651Brian
39800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_INTERNAL:
39900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      {
40000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         switch (state[1]) {
40100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	    case STATE_TEXRECT_SCALE: {
40200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   	       const int unit = (int) state[2];
40300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	       const struct gl_texture_object *texObj = ctx->Texture.Unit[unit]._Current;
40400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	       if (texObj) {
40500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian		  struct gl_texture_image *texImage = texObj->Image[0][0];
40600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian		  ASSIGN_4V(value, 1.0 / texImage->Width, 1.0 / texImage->Height, 0, 1);
40700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	       }
40800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               break;
40900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	    }
41000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	    default:
41100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	       /* unknown state indexes are silently ignored
41200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	       *  should be handled by the driver.
41300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	       */
41400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian               return;
41500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         }
41600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
41700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
41800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
41900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   default:
42000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      _mesa_problem(ctx, "Invalid state in _mesa_fetch_state");
42100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
42200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   }
42300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian}
42400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
42500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
42600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian/**
42700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * Return a bitmask of the Mesa state flags (_NEW_* values) which would
42800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * indicate that the given context state may have changed.
42900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * The bitmask is used during validation to determine if we need to update
43000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * vertex/fragment program parameters (like "state.material.color") when
43100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * some GL state has changed.
43200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian */
43300cdc0a472c55330cbc58317f01b07f8f90be5a5BrianGLbitfield
434aa9d22a1c0f3256497088985c290d4046e089456Brian_mesa_program_state_flags(const gl_state_index state[STATE_LENGTH])
43500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian{
43600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   switch (state[0]) {
43700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_MATERIAL:
43800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHT:
43900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHTMODEL_AMBIENT:
44000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHTMODEL_SCENECOLOR:
44100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHTPROD:
44200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return _NEW_LIGHT;
44300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
44400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXGEN:
44500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXENV_COLOR:
44600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return _NEW_TEXTURE;
44700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
44800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_FOG_COLOR:
44900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_FOG_PARAMS:
45000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return _NEW_FOG;
45100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
45200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_CLIPPLANE:
45300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return _NEW_TRANSFORM;
45400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
455776bc9cf55b116e17dddde4d097985b51879c83fBrian   case STATE_POINT_SIZE:
456776bc9cf55b116e17dddde4d097985b51879c83fBrian   case STATE_POINT_ATTENUATION:
45700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return _NEW_POINT;
45800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
4596531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_MODELVIEW_MATRIX:
4606531952b3c979be0dc95704beb3c3b9dad1dc37bBrian      return _NEW_MODELVIEW;
4616531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_PROJECTION_MATRIX:
4626531952b3c979be0dc95704beb3c3b9dad1dc37bBrian      return _NEW_PROJECTION;
4636531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_MVP_MATRIX:
4646531952b3c979be0dc95704beb3c3b9dad1dc37bBrian      return _NEW_MODELVIEW | _NEW_PROJECTION;
4656531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_TEXTURE_MATRIX:
4666531952b3c979be0dc95704beb3c3b9dad1dc37bBrian      return _NEW_TEXTURE_MATRIX;
4676531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_PROGRAM_MATRIX:
4686531952b3c979be0dc95704beb3c3b9dad1dc37bBrian      return _NEW_TRACK_MATRIX;
46900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
47000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_DEPTH_RANGE:
47100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return _NEW_VIEWPORT;
47200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
47300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_FRAGMENT_PROGRAM:
47400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_VERTEX_PROGRAM:
47500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return _NEW_PROGRAM;
47600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
477f958aabdf3e3dc82827628cab97b159bd5089651Brian   case STATE_NORMAL_SCALE:
478f958aabdf3e3dc82827628cab97b159bd5089651Brian      return _NEW_MODELVIEW;
479f958aabdf3e3dc82827628cab97b159bd5089651Brian
48000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_INTERNAL:
48100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      switch (state[1]) {
48200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      case STATE_TEXRECT_SCALE:
48300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	 return _NEW_TEXTURE;
48400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      default:
48500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         /* unknown state indexes are silently ignored and
48600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         *  no flag set, since it is handled by the driver.
48700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         */
48800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian	 return 0;
48900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
49000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
49100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   default:
49200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      _mesa_problem(NULL, "unexpected state[0] in make_state_flags()");
49300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return 0;
49400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   }
49500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian}
49600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
49700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
49800cdc0a472c55330cbc58317f01b07f8f90be5a5Brianstatic void
49900cdc0a472c55330cbc58317f01b07f8f90be5a5Brianappend(char *dst, const char *src)
50000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian{
50100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   while (*dst)
50200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      dst++;
50300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   while (*src)
50400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian     *dst++ = *src++;
50500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   *dst = 0;
50600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian}
50700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
50800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
50900cdc0a472c55330cbc58317f01b07f8f90be5a5Brianstatic void
51000cdc0a472c55330cbc58317f01b07f8f90be5a5Brianappend_token(char *dst, gl_state_index k)
51100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian{
51200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   switch (k) {
51300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_MATERIAL:
514f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, "material");
51500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
51600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHT:
51700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "light");
51800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
51900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHTMODEL_AMBIENT:
52000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "lightmodel.ambient");
52100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
52200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHTMODEL_SCENECOLOR:
52300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
52400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHTPROD:
52500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "lightprod");
52600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
52700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXGEN:
52800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "texgen");
52900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
53000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_FOG_COLOR:
531776bc9cf55b116e17dddde4d097985b51879c83fBrian      append(dst, "fog.color");
53200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
53300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_FOG_PARAMS:
534776bc9cf55b116e17dddde4d097985b51879c83fBrian      append(dst, "fog.params");
53500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
53600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_CLIPPLANE:
53700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "clip");
53800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
53900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_POINT_SIZE:
540776bc9cf55b116e17dddde4d097985b51879c83fBrian      append(dst, "point.size");
54100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
54200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_POINT_ATTENUATION:
543776bc9cf55b116e17dddde4d097985b51879c83fBrian      append(dst, "point.attenuation");
54400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
5456531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_MODELVIEW_MATRIX:
546f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, "matrix.modelview");
54700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
5486531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_PROJECTION_MATRIX:
549f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, "matrix.projection");
55000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
5516531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_MVP_MATRIX:
552f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, "matrix.mvp");
55300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
5546531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_TEXTURE_MATRIX:
555f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, "matrix.texture");
55600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
5576531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_PROGRAM_MATRIX:
558f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, "matrix.program");
55900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
56000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_MATRIX_INVERSE:
56100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, ".inverse");
56200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
56300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_MATRIX_TRANSPOSE:
56400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, ".transpose");
56500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
56600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_MATRIX_INVTRANS:
56700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, ".invtrans");
56800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
56900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_AMBIENT:
570f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, ".ambient");
57100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
57200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_DIFFUSE:
573f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, ".diffuse");
57400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
57500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_SPECULAR:
576f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, ".specular");
57700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
57800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_EMISSION:
579f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, ".emission");
58000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
58100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_SHININESS:
582f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, "lshininess");
58300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
584f958aabdf3e3dc82827628cab97b159bd5089651Brian   case STATE_HALF_VECTOR:
585f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, ".half");
58600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
58700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_POSITION:
58800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, ".position");
58900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
59000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_ATTENUATION:
59100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, ".attenuation");
59200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
59300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_SPOT_DIRECTION:
59400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, ".spot.direction");
59500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
596f958aabdf3e3dc82827628cab97b159bd5089651Brian   case STATE_SPOT_CUTOFF:
597f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, ".spot.cutoff");
598f958aabdf3e3dc82827628cab97b159bd5089651Brian      break;
59900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXGEN_EYE_S:
60000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "eye.s");
60100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
60200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXGEN_EYE_T:
60300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "eye.t");
60400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
60500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXGEN_EYE_R:
60600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "eye.r");
60700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
60800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXGEN_EYE_Q:
60900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "eye.q");
61000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
61100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXGEN_OBJECT_S:
61200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "object.s");
61300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
61400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXGEN_OBJECT_T:
61500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "object.t");
61600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
61700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXGEN_OBJECT_R:
61800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "object.r");
61900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
62000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXGEN_OBJECT_Q:
62100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "object.q");
62200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
62300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXENV_COLOR:
62400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "texenv");
62500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
62600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_DEPTH_RANGE:
62700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "depth.range");
62800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
62900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_VERTEX_PROGRAM:
63000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_FRAGMENT_PROGRAM:
63100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
63200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_ENV:
63300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "env");
63400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
63500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LOCAL:
63600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "local");
63700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
63800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_NORMAL_SCALE:
639f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(dst, "normalScale");
640f958aabdf3e3dc82827628cab97b159bd5089651Brian      break;
641f958aabdf3e3dc82827628cab97b159bd5089651Brian   case STATE_INTERNAL:
64200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_POSITION_NORMALIZED:
64300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "(internal)");
64400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
64500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   default:
64600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      ;
64700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   }
64800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian}
64900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
65000cdc0a472c55330cbc58317f01b07f8f90be5a5Brianstatic void
65100cdc0a472c55330cbc58317f01b07f8f90be5a5Brianappend_face(char *dst, GLint face)
65200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian{
65300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   if (face == 0)
65400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "front.");
65500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   else
65600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(dst, "back.");
65700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian}
65800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
65900cdc0a472c55330cbc58317f01b07f8f90be5a5Brianstatic void
66000cdc0a472c55330cbc58317f01b07f8f90be5a5Brianappend_index(char *dst, GLint index)
66100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian{
66200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   char s[20];
663f958aabdf3e3dc82827628cab97b159bd5089651Brian   _mesa_sprintf(s, "[%d]", index);
66400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   append(dst, s);
66500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian}
66600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
66700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian/**
66800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * Make a string from the given state vector.
66900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * For example, return "state.matrix.texture[2].inverse".
67000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * Use _mesa_free() to deallocate the string.
67100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian */
67200cdc0a472c55330cbc58317f01b07f8f90be5a5Brianconst char *
673aa9d22a1c0f3256497088985c290d4046e089456Brian_mesa_program_state_string(const gl_state_index state[STATE_LENGTH])
67400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian{
67500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   char str[1000] = "";
67600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   char tmp[30];
67700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
67800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   append(str, "state.");
67900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   append_token(str, (gl_state_index) state[0]);
68000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
68100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   switch (state[0]) {
68200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_MATERIAL:
68300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_face(str, state[1]);
68400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_token(str, (gl_state_index) state[2]);
68500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
68600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHT:
68700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_index(str, state[1]); /* light number [i]. */
68800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_token(str, (gl_state_index) state[2]); /* coefficients */
68900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
69000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHTMODEL_AMBIENT:
69100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(str, "lightmodel.ambient");
69200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
69300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHTMODEL_SCENECOLOR:
69400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      if (state[1] == 0) {
69500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         append(str, "lightmodel.front.scenecolor");
69600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
69700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      else {
69800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         append(str, "lightmodel.back.scenecolor");
69900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
70000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
70100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_LIGHTPROD:
70200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_index(str, state[1]); /* light number [i]. */
70300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_face(str, state[2]);
70400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_token(str, (gl_state_index) state[3]);
70500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
70600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXGEN:
70700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_index(str, state[1]); /* tex unit [i] */
70800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_token(str, (gl_state_index) state[2]); /* plane coef */
70900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
71000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_TEXENV_COLOR:
71100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_index(str, state[1]); /* tex unit [i] */
71200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append(str, "color");
71300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
71400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_CLIPPLANE:
71500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_index(str, state[1]); /* plane [i] */
716f958aabdf3e3dc82827628cab97b159bd5089651Brian      append(str, ".plane");
71700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
7186531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_MODELVIEW_MATRIX:
7196531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_PROJECTION_MATRIX:
7206531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_MVP_MATRIX:
7216531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_TEXTURE_MATRIX:
7226531952b3c979be0dc95704beb3c3b9dad1dc37bBrian   case STATE_PROGRAM_MATRIX:
72300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      {
7246531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         /* state[0] = modelview, projection, texture, etc. */
7256531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         /* state[1] = which texture matrix or program matrix */
7266531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         /* state[2] = first row to fetch */
7276531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         /* state[3] = last row to fetch */
7286531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         /* state[4] = transpose, inverse or invtrans */
7296531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         const gl_state_index mat = (gl_state_index) state[0];
7306531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         const GLuint index = (GLuint) state[1];
7316531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         const GLuint firstRow = (GLuint) state[2];
7326531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         const GLuint lastRow = (GLuint) state[3];
7336531952b3c979be0dc95704beb3c3b9dad1dc37bBrian         const gl_state_index modifier = (gl_state_index) state[4];
734f958aabdf3e3dc82827628cab97b159bd5089651Brian         if (index ||
735f958aabdf3e3dc82827628cab97b159bd5089651Brian             mat == STATE_TEXTURE_MATRIX ||
736f958aabdf3e3dc82827628cab97b159bd5089651Brian             mat == STATE_PROGRAM_MATRIX)
73700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            append_index(str, index);
73800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         if (modifier)
73900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            append_token(str, modifier);
74000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         if (firstRow == lastRow)
74100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            _mesa_sprintf(tmp, ".row[%d]", firstRow);
74200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         else
74300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian            _mesa_sprintf(tmp, ".row[%d..%d]", firstRow, lastRow);
74400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         append(str, tmp);
74500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
74600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
747a2786a97d74647662f1fe6aa29257e70b9e3636aBrian   case STATE_POINT_SIZE:
748a2786a97d74647662f1fe6aa29257e70b9e3636aBrian      break;
749a2786a97d74647662f1fe6aa29257e70b9e3636aBrian   case STATE_POINT_ATTENUATION:
750a2786a97d74647662f1fe6aa29257e70b9e3636aBrian      break;
751a2786a97d74647662f1fe6aa29257e70b9e3636aBrian   case STATE_FOG_PARAMS:
752a2786a97d74647662f1fe6aa29257e70b9e3636aBrian      break;
753a2786a97d74647662f1fe6aa29257e70b9e3636aBrian   case STATE_FOG_COLOR:
754a2786a97d74647662f1fe6aa29257e70b9e3636aBrian      break;
75500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_DEPTH_RANGE:
75600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
75700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_FRAGMENT_PROGRAM:
75800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_VERTEX_PROGRAM:
75900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      /* state[1] = {STATE_ENV, STATE_LOCAL} */
76000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      /* state[2] = parameter index          */
76100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_token(str, (gl_state_index) state[1]);
76200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      append_index(str, state[2]);
76300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
76400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   case STATE_INTERNAL:
76500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
76600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   default:
76700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      _mesa_problem(NULL, "Invalid state in _mesa_program_state_string");
76800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      break;
76900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   }
77000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
77100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   return _mesa_strdup(str);
77200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian}
77300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
77400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
77500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian/**
77600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * Loop over all the parameters in a parameter list.  If the parameter
77700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * is a GL state reference, look up the current value of that state
77800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * variable and put it into the parameter's Value[4] array.
77900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian * This would be called at glBegin time when using a fragment program.
78000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian */
78100cdc0a472c55330cbc58317f01b07f8f90be5a5Brianvoid
78200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian_mesa_load_state_parameters(GLcontext *ctx,
78300cdc0a472c55330cbc58317f01b07f8f90be5a5Brian                            struct gl_program_parameter_list *paramList)
78400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian{
78500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   GLuint i;
78600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
78700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   if (!paramList)
78800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      return;
78900cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
79000cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   for (i = 0; i < paramList->NumParameters; i++) {
79100cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      if (paramList->Parameters[i].Type == PROGRAM_STATE_VAR) {
79200cdc0a472c55330cbc58317f01b07f8f90be5a5Brian         _mesa_fetch_state(ctx,
793223d7cb3c785ad58c869a3ee0fbf2f1d42c3310dBrian			   (gl_state_index *) paramList->Parameters[i].StateIndexes,
79400cdc0a472c55330cbc58317f01b07f8f90be5a5Brian                           paramList->ParameterValues[i]);
79500cdc0a472c55330cbc58317f01b07f8f90be5a5Brian      }
79600cdc0a472c55330cbc58317f01b07f8f90be5a5Brian   }
79700cdc0a472c55330cbc58317f01b07f8f90be5a5Brian}
79800cdc0a472c55330cbc58317f01b07f8f90be5a5Brian
799