attrib.c revision 798d83cf67098a7df293c711e0d2c8c296fc4c8f
1/* $Id: attrib.c,v 1.74 2002/10/17 22:26:06 kschultz Exp $ */ 2 3/* 4 * Mesa 3-D graphics library 5 * Version: 4.1 6 * 7 * Copyright (C) 1999-2002 Brian Paul All Rights Reserved. 8 * 9 * Permission is hereby granted, free of charge, to any person obtaining a 10 * copy of this software and associated documentation files (the "Software"), 11 * to deal in the Software without restriction, including without limitation 12 * the rights to use, copy, modify, merge, publish, distribute, sublicense, 13 * and/or sell copies of the Software, and to permit persons to whom the 14 * Software is furnished to do so, subject to the following conditions: 15 * 16 * The above copyright notice and this permission notice shall be included 17 * in all copies or substantial portions of the Software. 18 * 19 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS 20 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 21 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 22 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN 23 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN 24 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 25 */ 26 27 28#ifdef PC_HEADER 29#include "all.h" 30#else 31#include "glheader.h" 32#include "accum.h" 33#include "attrib.h" 34#include "blend.h" 35#include "buffers.h" 36#include "colormac.h" 37#include "context.h" 38#include "depth.h" 39#include "enable.h" 40#include "enums.h" 41#include "fog.h" 42#include "hint.h" 43#include "light.h" 44#include "lines.h" 45#include "matrix.h" 46#include "mem.h" 47#include "points.h" 48#include "polygon.h" 49#include "simple_list.h" 50#include "stencil.h" 51#include "texobj.h" 52#include "texstate.h" 53#include "mtypes.h" 54#include "math/m_xform.h" 55#endif 56 57 58 59 60/* 61 * Allocate a new attribute state node. These nodes have a 62 * "kind" value and a pointer to a struct of state data. 63 */ 64static struct gl_attrib_node * 65new_attrib_node( GLbitfield kind ) 66{ 67 struct gl_attrib_node *an = MALLOC_STRUCT(gl_attrib_node); 68 if (an) { 69 an->kind = kind; 70 } 71 return an; 72} 73 74 75void 76_mesa_PushAttrib(GLbitfield mask) 77{ 78 struct gl_attrib_node *newnode; 79 struct gl_attrib_node *head; 80 81 GET_CURRENT_CONTEXT(ctx); 82 ASSERT_OUTSIDE_BEGIN_END(ctx); 83 84 if (MESA_VERBOSE & VERBOSE_API) 85 _mesa_debug(ctx, "glPushAttrib %x\n", (int) mask); 86 87 if (ctx->AttribStackDepth >= MAX_ATTRIB_STACK_DEPTH) { 88 _mesa_error( ctx, GL_STACK_OVERFLOW, "glPushAttrib" ); 89 return; 90 } 91 92 /* Build linked list of attribute nodes which save all attribute */ 93 /* groups specified by the mask. */ 94 head = NULL; 95 96 if (mask & GL_ACCUM_BUFFER_BIT) { 97 struct gl_accum_attrib *attr; 98 attr = MALLOC_STRUCT( gl_accum_attrib ); 99 MEMCPY( attr, &ctx->Accum, sizeof(struct gl_accum_attrib) ); 100 newnode = new_attrib_node( GL_ACCUM_BUFFER_BIT ); 101 newnode->data = attr; 102 newnode->next = head; 103 head = newnode; 104 } 105 106 if (mask & GL_COLOR_BUFFER_BIT) { 107 struct gl_colorbuffer_attrib *attr; 108 attr = MALLOC_STRUCT( gl_colorbuffer_attrib ); 109 MEMCPY( attr, &ctx->Color, sizeof(struct gl_colorbuffer_attrib) ); 110 newnode = new_attrib_node( GL_COLOR_BUFFER_BIT ); 111 newnode->data = attr; 112 newnode->next = head; 113 head = newnode; 114 } 115 116 if (mask & GL_CURRENT_BIT) { 117 struct gl_current_attrib *attr; 118 FLUSH_CURRENT( ctx, 0 ); 119 attr = MALLOC_STRUCT( gl_current_attrib ); 120 MEMCPY( attr, &ctx->Current, sizeof(struct gl_current_attrib) ); 121 newnode = new_attrib_node( GL_CURRENT_BIT ); 122 newnode->data = attr; 123 newnode->next = head; 124 head = newnode; 125 } 126 127 if (mask & GL_DEPTH_BUFFER_BIT) { 128 struct gl_depthbuffer_attrib *attr; 129 attr = MALLOC_STRUCT( gl_depthbuffer_attrib ); 130 MEMCPY( attr, &ctx->Depth, sizeof(struct gl_depthbuffer_attrib) ); 131 newnode = new_attrib_node( GL_DEPTH_BUFFER_BIT ); 132 newnode->data = attr; 133 newnode->next = head; 134 head = newnode; 135 } 136 137 if (mask & GL_ENABLE_BIT) { 138 struct gl_enable_attrib *attr; 139 GLuint i; 140 attr = MALLOC_STRUCT( gl_enable_attrib ); 141 /* Copy enable flags from all other attributes into the enable struct. */ 142 attr->AlphaTest = ctx->Color.AlphaEnabled; 143 attr->AutoNormal = ctx->Eval.AutoNormal; 144 attr->Blend = ctx->Color.BlendEnabled; 145 attr->ClipPlanes = ctx->Transform.ClipPlanesEnabled; 146 attr->ColorMaterial = ctx->Light.ColorMaterialEnabled; 147 attr->Convolution1D = ctx->Pixel.Convolution1DEnabled; 148 attr->Convolution2D = ctx->Pixel.Convolution2DEnabled; 149 attr->Separable2D = ctx->Pixel.Separable2DEnabled; 150 attr->CullFace = ctx->Polygon.CullFlag; 151 attr->DepthTest = ctx->Depth.Test; 152 attr->Dither = ctx->Color.DitherFlag; 153 attr->Fog = ctx->Fog.Enabled; 154 for (i=0;i<MAX_LIGHTS;i++) { 155 attr->Light[i] = ctx->Light.Light[i].Enabled; 156 } 157 attr->Lighting = ctx->Light.Enabled; 158 attr->LineSmooth = ctx->Line.SmoothFlag; 159 attr->LineStipple = ctx->Line.StippleFlag; 160 attr->Histogram = ctx->Pixel.HistogramEnabled; 161 attr->MinMax = ctx->Pixel.MinMaxEnabled; 162 attr->IndexLogicOp = ctx->Color.IndexLogicOpEnabled; 163 attr->ColorLogicOp = ctx->Color.ColorLogicOpEnabled; 164 attr->Map1Color4 = ctx->Eval.Map1Color4; 165 attr->Map1Index = ctx->Eval.Map1Index; 166 attr->Map1Normal = ctx->Eval.Map1Normal; 167 attr->Map1TextureCoord1 = ctx->Eval.Map1TextureCoord1; 168 attr->Map1TextureCoord2 = ctx->Eval.Map1TextureCoord2; 169 attr->Map1TextureCoord3 = ctx->Eval.Map1TextureCoord3; 170 attr->Map1TextureCoord4 = ctx->Eval.Map1TextureCoord4; 171 attr->Map1Vertex3 = ctx->Eval.Map1Vertex3; 172 attr->Map1Vertex4 = ctx->Eval.Map1Vertex4; 173 MEMCPY(attr->Map1Attrib, ctx->Eval.Map1Attrib, sizeof(ctx->Eval.Map1Attrib)); 174 attr->Map2Color4 = ctx->Eval.Map2Color4; 175 attr->Map2Index = ctx->Eval.Map2Index; 176 attr->Map2Normal = ctx->Eval.Map2Normal; 177 attr->Map2TextureCoord1 = ctx->Eval.Map2TextureCoord1; 178 attr->Map2TextureCoord2 = ctx->Eval.Map2TextureCoord2; 179 attr->Map2TextureCoord3 = ctx->Eval.Map2TextureCoord3; 180 attr->Map2TextureCoord4 = ctx->Eval.Map2TextureCoord4; 181 attr->Map2Vertex3 = ctx->Eval.Map2Vertex3; 182 attr->Map2Vertex4 = ctx->Eval.Map2Vertex4; 183 MEMCPY(attr->Map2Attrib, ctx->Eval.Map2Attrib, sizeof(ctx->Eval.Map2Attrib)); 184 attr->Normalize = ctx->Transform.Normalize; 185 attr->RasterPositionUnclipped = ctx->Transform.RasterPositionUnclipped; 186 attr->PixelTexture = ctx->Pixel.PixelTextureEnabled; 187 attr->PointSmooth = ctx->Point.SmoothFlag; 188 attr->PointSprite = ctx->Point.PointSprite; 189 attr->PolygonOffsetPoint = ctx->Polygon.OffsetPoint; 190 attr->PolygonOffsetLine = ctx->Polygon.OffsetLine; 191 attr->PolygonOffsetFill = ctx->Polygon.OffsetFill; 192 attr->PolygonSmooth = ctx->Polygon.SmoothFlag; 193 attr->PolygonStipple = ctx->Polygon.StippleFlag; 194 attr->RescaleNormals = ctx->Transform.RescaleNormals; 195 attr->Scissor = ctx->Scissor.Enabled; 196 attr->Stencil = ctx->Stencil.Enabled; 197 attr->MultisampleEnabled = ctx->Multisample.Enabled; 198 attr->SampleAlphaToCoverage = ctx->Multisample.SampleAlphaToCoverage; 199 attr->SampleAlphaToOne = ctx->Multisample.SampleAlphaToOne; 200 attr->SampleCoverage = ctx->Multisample.SampleCoverage; 201 attr->SampleCoverageInvert = ctx->Multisample.SampleCoverageInvert; 202 for (i=0; i<MAX_TEXTURE_UNITS; i++) { 203 attr->Texture[i] = ctx->Texture.Unit[i].Enabled; 204 attr->TexGen[i] = ctx->Texture.Unit[i].TexGenEnabled; 205 } 206 /* GL_NV_vertex_program */ 207 attr->VertexProgram = ctx->VertexProgram.Enabled; 208 attr->VertexProgramPointSize = ctx->VertexProgram.PointSizeEnabled; 209 attr->VertexProgramTwoSide = ctx->VertexProgram.TwoSideEnabled; 210 newnode = new_attrib_node( GL_ENABLE_BIT ); 211 newnode->data = attr; 212 newnode->next = head; 213 head = newnode; 214 } 215 216 if (mask & GL_EVAL_BIT) { 217 struct gl_eval_attrib *attr; 218 attr = MALLOC_STRUCT( gl_eval_attrib ); 219 MEMCPY( attr, &ctx->Eval, sizeof(struct gl_eval_attrib) ); 220 newnode = new_attrib_node( GL_EVAL_BIT ); 221 newnode->data = attr; 222 newnode->next = head; 223 head = newnode; 224 } 225 226 if (mask & GL_FOG_BIT) { 227 struct gl_fog_attrib *attr; 228 attr = MALLOC_STRUCT( gl_fog_attrib ); 229 MEMCPY( attr, &ctx->Fog, sizeof(struct gl_fog_attrib) ); 230 newnode = new_attrib_node( GL_FOG_BIT ); 231 newnode->data = attr; 232 newnode->next = head; 233 head = newnode; 234 } 235 236 if (mask & GL_HINT_BIT) { 237 struct gl_hint_attrib *attr; 238 attr = MALLOC_STRUCT( gl_hint_attrib ); 239 MEMCPY( attr, &ctx->Hint, sizeof(struct gl_hint_attrib) ); 240 newnode = new_attrib_node( GL_HINT_BIT ); 241 newnode->data = attr; 242 newnode->next = head; 243 head = newnode; 244 } 245 246 if (mask & GL_LIGHTING_BIT) { 247 struct gl_light_attrib *attr; 248 FLUSH_CURRENT(ctx, 0); /* flush material changes */ 249 attr = MALLOC_STRUCT( gl_light_attrib ); 250 MEMCPY( attr, &ctx->Light, sizeof(struct gl_light_attrib) ); 251 newnode = new_attrib_node( GL_LIGHTING_BIT ); 252 newnode->data = attr; 253 newnode->next = head; 254 head = newnode; 255 } 256 257 if (mask & GL_LINE_BIT) { 258 struct gl_line_attrib *attr; 259 attr = MALLOC_STRUCT( gl_line_attrib ); 260 MEMCPY( attr, &ctx->Line, sizeof(struct gl_line_attrib) ); 261 newnode = new_attrib_node( GL_LINE_BIT ); 262 newnode->data = attr; 263 newnode->next = head; 264 head = newnode; 265 } 266 267 if (mask & GL_LIST_BIT) { 268 struct gl_list_attrib *attr; 269 attr = MALLOC_STRUCT( gl_list_attrib ); 270 MEMCPY( attr, &ctx->List, sizeof(struct gl_list_attrib) ); 271 newnode = new_attrib_node( GL_LIST_BIT ); 272 newnode->data = attr; 273 newnode->next = head; 274 head = newnode; 275 } 276 277 if (mask & GL_PIXEL_MODE_BIT) { 278 struct gl_pixel_attrib *attr; 279 attr = MALLOC_STRUCT( gl_pixel_attrib ); 280 MEMCPY( attr, &ctx->Pixel, sizeof(struct gl_pixel_attrib) ); 281 newnode = new_attrib_node( GL_PIXEL_MODE_BIT ); 282 newnode->data = attr; 283 newnode->next = head; 284 head = newnode; 285 } 286 287 if (mask & GL_POINT_BIT) { 288 struct gl_point_attrib *attr; 289 attr = MALLOC_STRUCT( gl_point_attrib ); 290 MEMCPY( attr, &ctx->Point, sizeof(struct gl_point_attrib) ); 291 newnode = new_attrib_node( GL_POINT_BIT ); 292 newnode->data = attr; 293 newnode->next = head; 294 head = newnode; 295 } 296 297 if (mask & GL_POLYGON_BIT) { 298 struct gl_polygon_attrib *attr; 299 attr = MALLOC_STRUCT( gl_polygon_attrib ); 300 MEMCPY( attr, &ctx->Polygon, sizeof(struct gl_polygon_attrib) ); 301 newnode = new_attrib_node( GL_POLYGON_BIT ); 302 newnode->data = attr; 303 newnode->next = head; 304 head = newnode; 305 } 306 307 if (mask & GL_POLYGON_STIPPLE_BIT) { 308 GLuint *stipple; 309 stipple = (GLuint *) MALLOC( 32*sizeof(GLuint) ); 310 MEMCPY( stipple, ctx->PolygonStipple, 32*sizeof(GLuint) ); 311 newnode = new_attrib_node( GL_POLYGON_STIPPLE_BIT ); 312 newnode->data = stipple; 313 newnode->next = head; 314 head = newnode; 315 } 316 317 if (mask & GL_SCISSOR_BIT) { 318 struct gl_scissor_attrib *attr; 319 attr = MALLOC_STRUCT( gl_scissor_attrib ); 320 MEMCPY( attr, &ctx->Scissor, sizeof(struct gl_scissor_attrib) ); 321 newnode = new_attrib_node( GL_SCISSOR_BIT ); 322 newnode->data = attr; 323 newnode->next = head; 324 head = newnode; 325 } 326 327 if (mask & GL_STENCIL_BUFFER_BIT) { 328 struct gl_stencil_attrib *attr; 329 attr = MALLOC_STRUCT( gl_stencil_attrib ); 330 MEMCPY( attr, &ctx->Stencil, sizeof(struct gl_stencil_attrib) ); 331 newnode = new_attrib_node( GL_STENCIL_BUFFER_BIT ); 332 newnode->data = attr; 333 newnode->next = head; 334 head = newnode; 335 } 336 337 if (mask & GL_TEXTURE_BIT) { 338 struct gl_texture_attrib *attr; 339 GLuint u; 340 /* Bump the texture object reference counts so that they don't 341 * inadvertantly get deleted. 342 */ 343 for (u = 0; u < ctx->Const.MaxTextureUnits; u++) { 344 ctx->Texture.Unit[u].Current1D->RefCount++; 345 ctx->Texture.Unit[u].Current2D->RefCount++; 346 ctx->Texture.Unit[u].Current3D->RefCount++; 347 ctx->Texture.Unit[u].CurrentCubeMap->RefCount++; 348 ctx->Texture.Unit[u].CurrentRect->RefCount++; 349 } 350 attr = MALLOC_STRUCT( gl_texture_attrib ); 351 MEMCPY( attr, &ctx->Texture, sizeof(struct gl_texture_attrib) ); 352 /* copy state of the currently bound texture objects */ 353 for (u = 0; u < ctx->Const.MaxTextureUnits; u++) { 354 _mesa_copy_texture_object(&attr->Unit[u].Saved1D, 355 attr->Unit[u].Current1D); 356 _mesa_copy_texture_object(&attr->Unit[u].Saved2D, 357 attr->Unit[u].Current2D); 358 _mesa_copy_texture_object(&attr->Unit[u].Saved3D, 359 attr->Unit[u].Current3D); 360 _mesa_copy_texture_object(&attr->Unit[u].SavedCubeMap, 361 attr->Unit[u].CurrentCubeMap); 362 _mesa_copy_texture_object(&attr->Unit[u].SavedRect, 363 attr->Unit[u].CurrentRect); 364 } 365 newnode = new_attrib_node( GL_TEXTURE_BIT ); 366 newnode->data = attr; 367 newnode->next = head; 368 head = newnode; 369 } 370 371 if (mask & GL_TRANSFORM_BIT) { 372 struct gl_transform_attrib *attr; 373 attr = MALLOC_STRUCT( gl_transform_attrib ); 374 MEMCPY( attr, &ctx->Transform, sizeof(struct gl_transform_attrib) ); 375 newnode = new_attrib_node( GL_TRANSFORM_BIT ); 376 newnode->data = attr; 377 newnode->next = head; 378 head = newnode; 379 } 380 381 if (mask & GL_VIEWPORT_BIT) { 382 struct gl_viewport_attrib *attr; 383 attr = MALLOC_STRUCT( gl_viewport_attrib ); 384 MEMCPY( attr, &ctx->Viewport, sizeof(struct gl_viewport_attrib) ); 385 newnode = new_attrib_node( GL_VIEWPORT_BIT ); 386 newnode->data = attr; 387 newnode->next = head; 388 head = newnode; 389 } 390 391 /* GL_ARB_multisample */ 392 if (mask & GL_MULTISAMPLE_BIT_ARB) { 393 struct gl_multisample_attrib *attr; 394 attr = MALLOC_STRUCT( gl_multisample_attrib ); 395 MEMCPY( attr, &ctx->Multisample, sizeof(struct gl_multisample_attrib) ); 396 newnode = new_attrib_node( GL_MULTISAMPLE_BIT_ARB ); 397 newnode->data = attr; 398 newnode->next = head; 399 head = newnode; 400 } 401 402 ctx->AttribStack[ctx->AttribStackDepth] = head; 403 ctx->AttribStackDepth++; 404} 405 406 407 408static void 409pop_enable_group(GLcontext *ctx, const struct gl_enable_attrib *enable) 410{ 411 GLuint i; 412 413#define TEST_AND_UPDATE(VALUE, NEWVALUE, ENUM) \ 414 if ((VALUE) != (NEWVALUE)) { \ 415 _mesa_set_enable( ctx, ENUM, (NEWVALUE) ); \ 416 } 417 418 TEST_AND_UPDATE(ctx->Color.AlphaEnabled, enable->AlphaTest, GL_ALPHA_TEST); 419 TEST_AND_UPDATE(ctx->Color.BlendEnabled, enable->Blend, GL_BLEND); 420 421 for (i=0;i<MAX_CLIP_PLANES;i++) { 422 const GLuint mask = 1 << i; 423 if ((ctx->Transform.ClipPlanesEnabled & mask) != (enable->ClipPlanes & mask)) 424 _mesa_set_enable(ctx, (GLenum) (GL_CLIP_PLANE0 + i), 425 (GLboolean) ((enable->ClipPlanes & mask) ? GL_TRUE : GL_FALSE)); 426 } 427 428 TEST_AND_UPDATE(ctx->Light.ColorMaterialEnabled, enable->ColorMaterial, 429 GL_COLOR_MATERIAL); 430 TEST_AND_UPDATE(ctx->Polygon.CullFlag, enable->CullFace, GL_CULL_FACE); 431 TEST_AND_UPDATE(ctx->Depth.Test, enable->DepthTest, GL_DEPTH_TEST); 432 TEST_AND_UPDATE(ctx->Color.DitherFlag, enable->Dither, GL_DITHER); 433 TEST_AND_UPDATE(ctx->Pixel.Convolution1DEnabled, enable->Convolution1D, 434 GL_CONVOLUTION_1D); 435 TEST_AND_UPDATE(ctx->Pixel.Convolution2DEnabled, enable->Convolution2D, 436 GL_CONVOLUTION_2D); 437 TEST_AND_UPDATE(ctx->Pixel.Separable2DEnabled, enable->Separable2D, 438 GL_SEPARABLE_2D); 439 TEST_AND_UPDATE(ctx->Fog.Enabled, enable->Fog, GL_FOG); 440 TEST_AND_UPDATE(ctx->Light.Enabled, enable->Lighting, GL_LIGHTING); 441 TEST_AND_UPDATE(ctx->Line.SmoothFlag, enable->LineSmooth, GL_LINE_SMOOTH); 442 TEST_AND_UPDATE(ctx->Line.StippleFlag, enable->LineStipple, 443 GL_LINE_STIPPLE); 444 TEST_AND_UPDATE(ctx->Color.IndexLogicOpEnabled, enable->IndexLogicOp, 445 GL_INDEX_LOGIC_OP); 446 TEST_AND_UPDATE(ctx->Color.ColorLogicOpEnabled, enable->ColorLogicOp, 447 GL_COLOR_LOGIC_OP); 448 449 TEST_AND_UPDATE(ctx->Eval.Map1Color4, enable->Map1Color4, GL_MAP1_COLOR_4); 450 TEST_AND_UPDATE(ctx->Eval.Map1Index, enable->Map1Index, GL_MAP1_INDEX); 451 TEST_AND_UPDATE(ctx->Eval.Map1Normal, enable->Map1Normal, GL_MAP1_NORMAL); 452 TEST_AND_UPDATE(ctx->Eval.Map1TextureCoord1, enable->Map1TextureCoord1, 453 GL_MAP1_TEXTURE_COORD_1); 454 TEST_AND_UPDATE(ctx->Eval.Map1TextureCoord2, enable->Map1TextureCoord2, 455 GL_MAP1_TEXTURE_COORD_2); 456 TEST_AND_UPDATE(ctx->Eval.Map1TextureCoord3, enable->Map1TextureCoord3, 457 GL_MAP1_TEXTURE_COORD_3); 458 TEST_AND_UPDATE(ctx->Eval.Map1TextureCoord4, enable->Map1TextureCoord4, 459 GL_MAP1_TEXTURE_COORD_4); 460 TEST_AND_UPDATE(ctx->Eval.Map1Vertex3, enable->Map1Vertex3, 461 GL_MAP1_VERTEX_3); 462 TEST_AND_UPDATE(ctx->Eval.Map1Vertex4, enable->Map1Vertex4, 463 GL_MAP1_VERTEX_4); 464 for (i = 0; i < 16; i++) { 465 TEST_AND_UPDATE(ctx->Eval.Map1Attrib[i], enable->Map1Attrib[i], 466 GL_MAP1_VERTEX_ATTRIB0_4_NV + i); 467 } 468 469 TEST_AND_UPDATE(ctx->Eval.Map2Color4, enable->Map2Color4, GL_MAP2_COLOR_4); 470 TEST_AND_UPDATE(ctx->Eval.Map2Index, enable->Map2Index, GL_MAP2_INDEX); 471 TEST_AND_UPDATE(ctx->Eval.Map2Normal, enable->Map2Normal, GL_MAP2_NORMAL); 472 TEST_AND_UPDATE(ctx->Eval.Map2TextureCoord1, enable->Map2TextureCoord1, 473 GL_MAP2_TEXTURE_COORD_1); 474 TEST_AND_UPDATE(ctx->Eval.Map2TextureCoord2, enable->Map2TextureCoord2, 475 GL_MAP2_TEXTURE_COORD_2); 476 TEST_AND_UPDATE(ctx->Eval.Map2TextureCoord3, enable->Map2TextureCoord3, 477 GL_MAP2_TEXTURE_COORD_3); 478 TEST_AND_UPDATE(ctx->Eval.Map2TextureCoord4, enable->Map2TextureCoord4, 479 GL_MAP2_TEXTURE_COORD_4); 480 TEST_AND_UPDATE(ctx->Eval.Map2Vertex3, enable->Map2Vertex3, 481 GL_MAP2_VERTEX_3); 482 TEST_AND_UPDATE(ctx->Eval.Map2Vertex4, enable->Map2Vertex4, 483 GL_MAP2_VERTEX_4); 484 for (i = 0; i < 16; i++) { 485 TEST_AND_UPDATE(ctx->Eval.Map2Attrib[i], enable->Map2Attrib[i], 486 GL_MAP2_VERTEX_ATTRIB0_4_NV + i); 487 } 488 489 TEST_AND_UPDATE(ctx->Eval.AutoNormal, enable->AutoNormal, GL_AUTO_NORMAL); 490 TEST_AND_UPDATE(ctx->Transform.Normalize, enable->Normalize, GL_NORMALIZE); 491 TEST_AND_UPDATE(ctx->Transform.RescaleNormals, enable->RescaleNormals, 492 GL_RESCALE_NORMAL_EXT); 493 TEST_AND_UPDATE(ctx->Transform.RasterPositionUnclipped, 494 enable->RasterPositionUnclipped, 495 GL_RASTER_POSITION_UNCLIPPED_IBM); 496 TEST_AND_UPDATE(ctx->Pixel.PixelTextureEnabled, enable->PixelTexture, 497 GL_POINT_SMOOTH); 498 TEST_AND_UPDATE(ctx->Point.SmoothFlag, enable->PointSmooth, 499 GL_POINT_SMOOTH); 500 if (ctx->Extensions.NV_point_sprite) { 501 TEST_AND_UPDATE(ctx->Point.PointSprite, enable->PointSprite, 502 GL_POINT_SPRITE_NV); 503 } 504 TEST_AND_UPDATE(ctx->Polygon.OffsetPoint, enable->PolygonOffsetPoint, 505 GL_POLYGON_OFFSET_POINT); 506 TEST_AND_UPDATE(ctx->Polygon.OffsetLine, enable->PolygonOffsetLine, 507 GL_POLYGON_OFFSET_LINE); 508 TEST_AND_UPDATE(ctx->Polygon.OffsetFill, enable->PolygonOffsetFill, 509 GL_POLYGON_OFFSET_FILL); 510 TEST_AND_UPDATE(ctx->Polygon.SmoothFlag, enable->PolygonSmooth, 511 GL_POLYGON_SMOOTH); 512 TEST_AND_UPDATE(ctx->Polygon.StippleFlag, enable->PolygonStipple, 513 GL_POLYGON_STIPPLE); 514 TEST_AND_UPDATE(ctx->Scissor.Enabled, enable->Scissor, GL_SCISSOR_TEST); 515 TEST_AND_UPDATE(ctx->Stencil.Enabled, enable->Stencil, GL_STENCIL_TEST); 516 /* XXX two-sided stencil */ 517 TEST_AND_UPDATE(ctx->Multisample.Enabled, enable->MultisampleEnabled, 518 GL_MULTISAMPLE_ARB); 519 TEST_AND_UPDATE(ctx->Multisample.SampleAlphaToCoverage, 520 enable->SampleAlphaToCoverage, 521 GL_SAMPLE_ALPHA_TO_COVERAGE_ARB); 522 TEST_AND_UPDATE(ctx->Multisample.SampleAlphaToOne, 523 enable->SampleAlphaToOne, 524 GL_SAMPLE_ALPHA_TO_ONE_ARB); 525 TEST_AND_UPDATE(ctx->Multisample.SampleCoverage, 526 enable->SampleCoverage, 527 GL_SAMPLE_COVERAGE_ARB); 528 TEST_AND_UPDATE(ctx->Multisample.SampleCoverageInvert, 529 enable->SampleCoverageInvert, 530 GL_SAMPLE_COVERAGE_INVERT_ARB); 531 /* GL_NV_vertex_program */ 532 TEST_AND_UPDATE(ctx->VertexProgram.Enabled, 533 enable->VertexProgram, 534 GL_VERTEX_PROGRAM_NV); 535 TEST_AND_UPDATE(ctx->VertexProgram.PointSizeEnabled, 536 enable->VertexProgramPointSize, 537 GL_VERTEX_PROGRAM_POINT_SIZE_NV); 538 TEST_AND_UPDATE(ctx->VertexProgram.TwoSideEnabled, 539 enable->VertexProgramTwoSide, 540 GL_VERTEX_PROGRAM_TWO_SIDE_NV); 541 542#undef TEST_AND_UPDATE 543 544 /* texture unit enables */ 545 for (i = 0; i < ctx->Const.MaxTextureUnits; i++) { 546 if (ctx->Texture.Unit[i].Enabled != enable->Texture[i]) { 547 ctx->Texture.Unit[i].Enabled = enable->Texture[i]; 548 if (ctx->Driver.Enable) { 549 if (ctx->Driver.ActiveTexture) { 550 (*ctx->Driver.ActiveTexture)(ctx, i); 551 } 552 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_1D, 553 (GLboolean) (enable->Texture[i] & TEXTURE_1D_BIT) ); 554 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_2D, 555 (GLboolean) (enable->Texture[i] & TEXTURE_2D_BIT) ); 556 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_3D, 557 (GLboolean) (enable->Texture[i] & TEXTURE_3D_BIT) ); 558 if (ctx->Extensions.ARB_texture_cube_map) 559 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_CUBE_MAP_ARB, 560 (GLboolean) (enable->Texture[i] & TEXTURE_CUBE_BIT) ); 561 if (ctx->Extensions.NV_texture_rectangle) 562 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_RECTANGLE_NV, 563 (GLboolean) (enable->Texture[i] & TEXTURE_RECT_BIT) ); 564 } 565 } 566 567 if (ctx->Texture.Unit[i].TexGenEnabled != enable->TexGen[i]) { 568 ctx->Texture.Unit[i].TexGenEnabled = enable->TexGen[i]; 569 if (ctx->Driver.Enable) { 570 if (ctx->Driver.ActiveTexture) { 571 (*ctx->Driver.ActiveTexture)(ctx, i); 572 } 573 if (enable->TexGen[i] & S_BIT) 574 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_GEN_S, GL_TRUE); 575 else 576 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_GEN_S, GL_FALSE); 577 if (enable->TexGen[i] & T_BIT) 578 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_GEN_T, GL_TRUE); 579 else 580 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_GEN_T, GL_FALSE); 581 if (enable->TexGen[i] & R_BIT) 582 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_GEN_R, GL_TRUE); 583 else 584 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_GEN_R, GL_FALSE); 585 if (enable->TexGen[i] & Q_BIT) 586 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_GEN_Q, GL_TRUE); 587 else 588 (*ctx->Driver.Enable)( ctx, GL_TEXTURE_GEN_Q, GL_FALSE); 589 } 590 } 591 } 592 593 if (ctx->Driver.ActiveTexture) { 594 (*ctx->Driver.ActiveTexture)(ctx, ctx->Texture.CurrentUnit); 595 } 596} 597 598 599static void 600pop_texture_group(GLcontext *ctx, const struct gl_texture_attrib *texAttrib) 601{ 602 GLuint u; 603 604 for (u = 0; u < ctx->Const.MaxTextureUnits; u++) { 605 const struct gl_texture_unit *unit = &texAttrib->Unit[u]; 606 GLuint i; 607 608 _mesa_ActiveTextureARB(GL_TEXTURE0_ARB + u); 609 _mesa_set_enable(ctx, GL_TEXTURE_1D, 610 (GLboolean) (unit->Enabled & TEXTURE_1D_BIT ? GL_TRUE : GL_FALSE)); 611 _mesa_set_enable(ctx, GL_TEXTURE_2D, 612 (GLboolean) (unit->Enabled & TEXTURE_2D_BIT ? GL_TRUE : GL_FALSE)); 613 _mesa_set_enable(ctx, GL_TEXTURE_3D, 614 (GLboolean) (unit->Enabled & TEXTURE_3D_BIT ? GL_TRUE : GL_FALSE)); 615 if (ctx->Extensions.ARB_texture_cube_map) { 616 _mesa_set_enable(ctx, GL_TEXTURE_CUBE_MAP_ARB, 617 (GLboolean) (unit->Enabled & TEXTURE_CUBE_BIT ? GL_TRUE : GL_FALSE)); 618 } 619 if (ctx->Extensions.NV_texture_rectangle) { 620 _mesa_set_enable(ctx, GL_TEXTURE_RECTANGLE_NV, 621 (GLboolean) (unit->Enabled & TEXTURE_RECT_BIT ? GL_TRUE : GL_FALSE)); 622 } 623 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, unit->EnvMode); 624 _mesa_TexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_COLOR, unit->EnvColor); 625 _mesa_TexGeni(GL_S, GL_TEXTURE_GEN_MODE, unit->GenModeS); 626 _mesa_TexGeni(GL_T, GL_TEXTURE_GEN_MODE, unit->GenModeT); 627 _mesa_TexGeni(GL_R, GL_TEXTURE_GEN_MODE, unit->GenModeR); 628 _mesa_TexGeni(GL_Q, GL_TEXTURE_GEN_MODE, unit->GenModeQ); 629 _mesa_TexGenfv(GL_S, GL_OBJECT_PLANE, unit->ObjectPlaneS); 630 _mesa_TexGenfv(GL_T, GL_OBJECT_PLANE, unit->ObjectPlaneT); 631 _mesa_TexGenfv(GL_R, GL_OBJECT_PLANE, unit->ObjectPlaneR); 632 _mesa_TexGenfv(GL_Q, GL_OBJECT_PLANE, unit->ObjectPlaneQ); 633 _mesa_TexGenfv(GL_S, GL_EYE_PLANE, unit->EyePlaneS); 634 _mesa_TexGenfv(GL_T, GL_EYE_PLANE, unit->EyePlaneT); 635 _mesa_TexGenfv(GL_R, GL_EYE_PLANE, unit->EyePlaneR); 636 _mesa_TexGenfv(GL_Q, GL_EYE_PLANE, unit->EyePlaneQ); 637 if (ctx->Extensions.EXT_texture_lod_bias) { 638 _mesa_TexEnvf(GL_TEXTURE_FILTER_CONTROL_EXT, 639 GL_TEXTURE_LOD_BIAS_EXT, unit->LodBias); 640 } 641 if (ctx->Extensions.EXT_texture_env_combine || 642 ctx->Extensions.ARB_texture_env_combine) { 643 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_COMBINE_RGB_EXT, 644 unit->CombineModeRGB); 645 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_COMBINE_ALPHA_EXT, 646 unit->CombineModeA); 647 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_RGB_EXT, 648 unit->CombineSourceRGB[0]); 649 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_RGB_EXT, 650 unit->CombineSourceRGB[1]); 651 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_SOURCE2_RGB_EXT, 652 unit->CombineSourceRGB[2]); 653 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_SOURCE0_ALPHA_EXT, 654 unit->CombineSourceA[0]); 655 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_SOURCE1_ALPHA_EXT, 656 unit->CombineSourceA[1]); 657 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_SOURCE2_ALPHA_EXT, 658 unit->CombineSourceA[2]); 659 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_RGB_EXT, 660 unit->CombineOperandRGB[0]); 661 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_RGB_EXT, 662 unit->CombineOperandRGB[1]); 663 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_OPERAND2_RGB_EXT, 664 unit->CombineOperandRGB[2]); 665 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_OPERAND0_ALPHA_EXT, 666 unit->CombineOperandA[0]); 667 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_OPERAND1_ALPHA_EXT, 668 unit->CombineOperandA[1]); 669 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_OPERAND2_ALPHA_EXT, 670 unit->CombineOperandA[2]); 671 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_RGB_SCALE_EXT, 672 1 << unit->CombineScaleShiftRGB); 673 _mesa_TexEnvi(GL_TEXTURE_ENV, GL_ALPHA_SCALE, 674 1 << unit->CombineScaleShiftA); 675 } 676 677 /* Restore texture object state */ 678 for (i = 0; i < NUM_TEXTURE_TARGETS; i++) { 679 GLenum target = 0; 680 const struct gl_texture_object *obj = NULL; 681 GLfloat bordColor[4]; 682 683 switch (i) { 684 case 0: 685 target = GL_TEXTURE_1D; 686 obj = &unit->Saved1D; 687 break; 688 case 1: 689 target = GL_TEXTURE_2D; 690 obj = &unit->Saved2D; 691 break; 692 case 2: 693 target = GL_TEXTURE_3D; 694 obj = &unit->Saved3D; 695 break; 696 case 3: 697 if (!ctx->Extensions.ARB_texture_cube_map) 698 continue; 699 target = GL_TEXTURE_CUBE_MAP_ARB; 700 obj = &unit->SavedCubeMap; 701 break; 702 case 4: 703 if (!ctx->Extensions.NV_texture_rectangle) 704 continue; 705 target = GL_TEXTURE_RECTANGLE_NV; 706 obj = &unit->SavedRect; 707 break; 708 default: 709 ; /* silence warnings */ 710 } 711 712 _mesa_BindTexture(target, obj->Name); 713 714 bordColor[0] = CHAN_TO_FLOAT(obj->BorderColor[0]); 715 bordColor[1] = CHAN_TO_FLOAT(obj->BorderColor[1]); 716 bordColor[2] = CHAN_TO_FLOAT(obj->BorderColor[2]); 717 bordColor[3] = CHAN_TO_FLOAT(obj->BorderColor[3]); 718 719 _mesa_TexParameterf(target, GL_TEXTURE_PRIORITY, obj->Priority); 720 _mesa_TexParameterfv(target, GL_TEXTURE_BORDER_COLOR, bordColor); 721 _mesa_TexParameteri(target, GL_TEXTURE_WRAP_S, obj->WrapS); 722 _mesa_TexParameteri(target, GL_TEXTURE_WRAP_T, obj->WrapT); 723 _mesa_TexParameteri(target, GL_TEXTURE_WRAP_R, obj->WrapR); 724 _mesa_TexParameteri(target, GL_TEXTURE_MIN_FILTER, obj->MinFilter); 725 _mesa_TexParameteri(target, GL_TEXTURE_MAG_FILTER, obj->MagFilter); 726 _mesa_TexParameterf(target, GL_TEXTURE_MIN_LOD, obj->MinLod); 727 _mesa_TexParameterf(target, GL_TEXTURE_MAX_LOD, obj->MaxLod); 728 _mesa_TexParameteri(target, GL_TEXTURE_BASE_LEVEL, obj->BaseLevel); 729 _mesa_TexParameteri(target, GL_TEXTURE_MAX_LEVEL, obj->MaxLevel); 730 if (ctx->Extensions.EXT_texture_filter_anisotropic) { 731 _mesa_TexParameterf(target, GL_TEXTURE_MAX_ANISOTROPY_EXT, 732 obj->MaxAnisotropy); 733 } 734 if (ctx->Extensions.SGIX_shadow) { 735 _mesa_TexParameteri(target, GL_TEXTURE_COMPARE_SGIX, 736 obj->CompareFlag); 737 _mesa_TexParameteri(target, GL_TEXTURE_COMPARE_OPERATOR_SGIX, 738 obj->CompareOperator); 739 } 740 if (ctx->Extensions.SGIX_shadow_ambient) { 741 _mesa_TexParameterf(target, GL_SHADOW_AMBIENT_SGIX, 742 obj->ShadowAmbient); 743 } 744 745 } 746 } 747 _mesa_ActiveTextureARB(GL_TEXTURE0_ARB 748 + texAttrib->CurrentUnit); 749 750 /* "un-bump" the texture object reference counts. We did that so they 751 * wouldn't inadvertantly get deleted while they were still referenced 752 * inside the attribute state stack. 753 */ 754 for (u = 0; u < ctx->Const.MaxTextureUnits; u++) { 755 ctx->Texture.Unit[u].Current1D->RefCount--; 756 ctx->Texture.Unit[u].Current2D->RefCount--; 757 ctx->Texture.Unit[u].Current3D->RefCount--; 758 ctx->Texture.Unit[u].CurrentCubeMap->RefCount--; 759 ctx->Texture.Unit[u].CurrentRect->RefCount--; 760 } 761} 762 763 764/* 765 * This function is kind of long just because we have to call a lot 766 * of device driver functions to update device driver state. 767 * 768 * XXX As it is now, most of the pop-code calls immediate-mode Mesa functions 769 * in order to restore GL state. This isn't terribly efficient but it 770 * ensures that dirty flags and any derived state gets updated correctly. 771 * We could at least check if the value to restore equals the current value 772 * and then skip the Mesa call. 773 */ 774void 775_mesa_PopAttrib(void) 776{ 777 struct gl_attrib_node *attr, *next; 778 GET_CURRENT_CONTEXT(ctx); 779 ASSERT_OUTSIDE_BEGIN_END_AND_FLUSH(ctx); 780 781 if (ctx->AttribStackDepth == 0) { 782 _mesa_error( ctx, GL_STACK_UNDERFLOW, "glPopAttrib" ); 783 return; 784 } 785 786 ctx->AttribStackDepth--; 787 attr = ctx->AttribStack[ctx->AttribStackDepth]; 788 789 while (attr) { 790 791 if (MESA_VERBOSE & VERBOSE_API) { 792 _mesa_debug(ctx, "glPopAttrib %s\n", 793 _mesa_lookup_enum_by_nr(attr->kind)); 794 } 795 796 switch (attr->kind) { 797 case GL_ACCUM_BUFFER_BIT: 798 { 799 const struct gl_accum_attrib *accum; 800 accum = (const struct gl_accum_attrib *) attr->data; 801 _mesa_ClearAccum(accum->ClearColor[0], 802 accum->ClearColor[1], 803 accum->ClearColor[2], 804 accum->ClearColor[3]); 805 } 806 break; 807 case GL_COLOR_BUFFER_BIT: 808 { 809 const struct gl_colorbuffer_attrib *color; 810 color = (const struct gl_colorbuffer_attrib *) attr->data; 811 _mesa_ClearIndex((GLfloat) color->ClearIndex); 812 _mesa_ClearColor(color->ClearColor[0], 813 color->ClearColor[1], 814 color->ClearColor[2], 815 color->ClearColor[3]); 816 _mesa_IndexMask(color->IndexMask); 817 _mesa_ColorMask((GLboolean) (color->ColorMask[0] != 0), 818 (GLboolean) (color->ColorMask[1] != 0), 819 (GLboolean) (color->ColorMask[2] != 0), 820 (GLboolean) (color->ColorMask[3] != 0)); 821 _mesa_DrawBuffer(color->DrawBuffer); 822 _mesa_set_enable(ctx, GL_ALPHA_TEST, color->AlphaEnabled); 823 _mesa_AlphaFunc(color->AlphaFunc, color->AlphaRef); 824 _mesa_set_enable(ctx, GL_BLEND, color->BlendEnabled); 825 _mesa_BlendFuncSeparateEXT(color->BlendSrcRGB, 826 color->BlendDstRGB, 827 color->BlendSrcA, 828 color->BlendDstA); 829 _mesa_BlendEquation(color->BlendEquation); 830 _mesa_BlendColor(color->BlendColor[0], 831 color->BlendColor[1], 832 color->BlendColor[2], 833 color->BlendColor[3]); 834 _mesa_LogicOp(color->LogicOp); 835 _mesa_set_enable(ctx, GL_COLOR_LOGIC_OP, 836 color->ColorLogicOpEnabled); 837 _mesa_set_enable(ctx, GL_INDEX_LOGIC_OP, 838 color->IndexLogicOpEnabled); 839 _mesa_set_enable(ctx, GL_DITHER, color->DitherFlag); 840 } 841 break; 842 case GL_CURRENT_BIT: 843 FLUSH_CURRENT( ctx, 0 ); 844 MEMCPY( &ctx->Current, attr->data, 845 sizeof(struct gl_current_attrib) ); 846 break; 847 case GL_DEPTH_BUFFER_BIT: 848 { 849 const struct gl_depthbuffer_attrib *depth; 850 depth = (const struct gl_depthbuffer_attrib *) attr->data; 851 _mesa_DepthFunc(depth->Func); 852 _mesa_ClearDepth(depth->Clear); 853 _mesa_set_enable(ctx, GL_DEPTH_TEST, depth->Test); 854 _mesa_DepthMask(depth->Mask); 855 if (ctx->Extensions.HP_occlusion_test) 856 _mesa_set_enable(ctx, GL_OCCLUSION_TEST_HP, 857 depth->OcclusionTest); 858 } 859 break; 860 case GL_ENABLE_BIT: 861 { 862 const struct gl_enable_attrib *enable; 863 enable = (const struct gl_enable_attrib *) attr->data; 864 pop_enable_group(ctx, enable); 865 ctx->NewState |= _NEW_ALL; 866 } 867 break; 868 case GL_EVAL_BIT: 869 MEMCPY( &ctx->Eval, attr->data, sizeof(struct gl_eval_attrib) ); 870 ctx->NewState |= _NEW_EVAL; 871 break; 872 case GL_FOG_BIT: 873 { 874 const struct gl_fog_attrib *fog; 875 fog = (const struct gl_fog_attrib *) attr->data; 876 _mesa_set_enable(ctx, GL_FOG, fog->Enabled); 877 _mesa_Fogfv(GL_FOG_COLOR, fog->Color); 878 _mesa_Fogf(GL_FOG_DENSITY, fog->Density); 879 _mesa_Fogf(GL_FOG_START, fog->Start); 880 _mesa_Fogf(GL_FOG_END, fog->End); 881 _mesa_Fogf(GL_FOG_INDEX, fog->Index); 882 _mesa_Fogi(GL_FOG_MODE, fog->Mode); 883 } 884 break; 885 case GL_HINT_BIT: 886 { 887 const struct gl_hint_attrib *hint; 888 hint = (const struct gl_hint_attrib *) attr->data; 889 _mesa_Hint(GL_PERSPECTIVE_CORRECTION_HINT, 890 hint->PerspectiveCorrection ); 891 _mesa_Hint(GL_POINT_SMOOTH_HINT, hint->PointSmooth); 892 _mesa_Hint(GL_LINE_SMOOTH_HINT, hint->LineSmooth); 893 _mesa_Hint(GL_POLYGON_SMOOTH_HINT, hint->PolygonSmooth); 894 _mesa_Hint(GL_FOG_HINT, hint->Fog); 895 _mesa_Hint(GL_CLIP_VOLUME_CLIPPING_HINT_EXT, 896 hint->ClipVolumeClipping); 897 if (ctx->Extensions.ARB_texture_compression) 898 _mesa_Hint(GL_TEXTURE_COMPRESSION_HINT_ARB, 899 hint->TextureCompression); 900 } 901 break; 902 case GL_LIGHTING_BIT: 903 { 904 GLuint i; 905 const struct gl_light_attrib *light; 906 light = (const struct gl_light_attrib *) attr->data; 907 /* lighting enable */ 908 _mesa_set_enable(ctx, GL_LIGHTING, light->Enabled); 909 /* per-light state */ 910 911 if (ctx->ModelviewMatrixStack.Top->flags & MAT_DIRTY_INVERSE) 912 _math_matrix_analyse( ctx->ModelviewMatrixStack.Top ); 913 914 for (i = 0; i < MAX_LIGHTS; i++) { 915 GLenum lgt = (GLenum) (GL_LIGHT0 + i); 916 const struct gl_light *l = &light->Light[i]; 917 GLfloat tmp[4]; 918 _mesa_set_enable(ctx, lgt, l->Enabled); 919 _mesa_Lightfv( lgt, GL_AMBIENT, l->Ambient ); 920 _mesa_Lightfv( lgt, GL_DIFFUSE, l->Diffuse ); 921 _mesa_Lightfv( lgt, GL_SPECULAR, l->Specular ); 922 TRANSFORM_POINT( tmp, ctx->ModelviewMatrixStack.Top->inv, l->EyePosition ); 923 _mesa_Lightfv( lgt, GL_POSITION, tmp ); 924 TRANSFORM_POINT( tmp, ctx->ModelviewMatrixStack.Top->m, l->EyeDirection ); 925 _mesa_Lightfv( lgt, GL_SPOT_DIRECTION, tmp ); 926 _mesa_Lightfv( lgt, GL_SPOT_EXPONENT, &l->SpotExponent ); 927 _mesa_Lightfv( lgt, GL_SPOT_CUTOFF, &l->SpotCutoff ); 928 _mesa_Lightfv( lgt, GL_CONSTANT_ATTENUATION, 929 &l->ConstantAttenuation ); 930 _mesa_Lightfv( lgt, GL_LINEAR_ATTENUATION, 931 &l->LinearAttenuation ); 932 _mesa_Lightfv( lgt, GL_QUADRATIC_ATTENUATION, 933 &l->QuadraticAttenuation ); 934 } 935 /* light model */ 936 _mesa_LightModelfv(GL_LIGHT_MODEL_AMBIENT, 937 light->Model.Ambient); 938 _mesa_LightModelf(GL_LIGHT_MODEL_LOCAL_VIEWER, 939 (GLfloat) light->Model.LocalViewer); 940 _mesa_LightModelf(GL_LIGHT_MODEL_TWO_SIDE, 941 (GLfloat) light->Model.TwoSide); 942 _mesa_LightModelf(GL_LIGHT_MODEL_COLOR_CONTROL, 943 (GLfloat) light->Model.ColorControl); 944 /* materials */ 945 MEMCPY(ctx->Light.Material, light->Material, 946 2 * sizeof(struct gl_material)); 947 /* shade model */ 948 _mesa_ShadeModel(light->ShadeModel); 949 /* color material */ 950 _mesa_ColorMaterial(light->ColorMaterialFace, 951 light->ColorMaterialMode); 952 _mesa_set_enable(ctx, GL_COLOR_MATERIAL, 953 light->ColorMaterialEnabled); 954 } 955 break; 956 case GL_LINE_BIT: 957 { 958 const struct gl_line_attrib *line; 959 line = (const struct gl_line_attrib *) attr->data; 960 _mesa_set_enable(ctx, GL_LINE_SMOOTH, line->SmoothFlag); 961 _mesa_set_enable(ctx, GL_LINE_STIPPLE, line->StippleFlag); 962 _mesa_LineStipple(line->StippleFactor, line->StipplePattern); 963 _mesa_LineWidth(line->Width); 964 } 965 break; 966 case GL_LIST_BIT: 967 MEMCPY( &ctx->List, attr->data, sizeof(struct gl_list_attrib) ); 968 break; 969 case GL_PIXEL_MODE_BIT: 970 MEMCPY( &ctx->Pixel, attr->data, sizeof(struct gl_pixel_attrib) ); 971 ctx->NewState |= _NEW_PIXEL; 972 break; 973 case GL_POINT_BIT: 974 { 975 const struct gl_point_attrib *point; 976 point = (const struct gl_point_attrib *) attr->data; 977 _mesa_PointSize(point->Size); 978 _mesa_set_enable(ctx, GL_POINT_SMOOTH, point->SmoothFlag); 979 if (ctx->Extensions.EXT_point_parameters) { 980 _mesa_PointParameterfvEXT(GL_DISTANCE_ATTENUATION_EXT, 981 point->Params); 982 _mesa_PointParameterfEXT(GL_POINT_SIZE_MIN_EXT, 983 point->MinSize); 984 _mesa_PointParameterfEXT(GL_POINT_SIZE_MAX_EXT, 985 point->MaxSize); 986 _mesa_PointParameterfEXT(GL_POINT_FADE_THRESHOLD_SIZE_EXT, 987 point->Threshold); 988 } 989 if (ctx->Extensions.NV_point_sprite) { 990 GLuint u; 991 for (u = 0; u < ctx->Const.MaxTextureUnits; u++) { 992 _mesa_TexEnvi(GL_POINT_SPRITE_NV, GL_COORD_REPLACE_NV, 993 (GLint) point->CoordReplace[u]); 994 } 995 _mesa_set_enable(ctx, GL_POINT_SPRITE_NV,point->PointSprite); 996 _mesa_PointParameteriNV(GL_POINT_SPRITE_R_MODE_NV, 997 ctx->Point.SpriteRMode); 998 } 999 } 1000 break; 1001 case GL_POLYGON_BIT: 1002 { 1003 const struct gl_polygon_attrib *polygon; 1004 polygon = (const struct gl_polygon_attrib *) attr->data; 1005 _mesa_CullFace(polygon->CullFaceMode); 1006 _mesa_FrontFace(polygon->FrontFace); 1007 _mesa_PolygonMode(GL_FRONT, polygon->FrontMode); 1008 _mesa_PolygonMode(GL_BACK, polygon->BackMode); 1009 _mesa_PolygonOffset(polygon->OffsetFactor, 1010 polygon->OffsetUnits); 1011 _mesa_set_enable(ctx, GL_POLYGON_SMOOTH, polygon->SmoothFlag); 1012 _mesa_set_enable(ctx, GL_POLYGON_STIPPLE, polygon->StippleFlag); 1013 _mesa_set_enable(ctx, GL_CULL_FACE, polygon->CullFlag); 1014 _mesa_set_enable(ctx, GL_POLYGON_OFFSET_POINT, 1015 polygon->OffsetPoint); 1016 _mesa_set_enable(ctx, GL_POLYGON_OFFSET_LINE, 1017 polygon->OffsetLine); 1018 _mesa_set_enable(ctx, GL_POLYGON_OFFSET_FILL, 1019 polygon->OffsetFill); 1020 } 1021 break; 1022 case GL_POLYGON_STIPPLE_BIT: 1023 MEMCPY( ctx->PolygonStipple, attr->data, 32*sizeof(GLuint) ); 1024 ctx->NewState |= _NEW_POLYGONSTIPPLE; 1025 if (ctx->Driver.PolygonStipple) 1026 ctx->Driver.PolygonStipple( ctx, (const GLubyte *) attr->data ); 1027 break; 1028 case GL_SCISSOR_BIT: 1029 { 1030 const struct gl_scissor_attrib *scissor; 1031 scissor = (const struct gl_scissor_attrib *) attr->data; 1032 _mesa_Scissor(scissor->X, scissor->Y, 1033 scissor->Width, scissor->Height); 1034 _mesa_set_enable(ctx, GL_SCISSOR_TEST, scissor->Enabled); 1035 } 1036 break; 1037 case GL_STENCIL_BUFFER_BIT: 1038 { 1039 const GLint face = 0; /* XXX stencil two side */ 1040 const struct gl_stencil_attrib *stencil; 1041 stencil = (const struct gl_stencil_attrib *) attr->data; 1042 _mesa_set_enable(ctx, GL_STENCIL_TEST, stencil->Enabled); 1043 _mesa_ClearStencil(stencil->Clear); 1044 _mesa_StencilFunc(stencil->Function[face], stencil->Ref[face], 1045 stencil->ValueMask[face]); 1046 _mesa_StencilMask(stencil->WriteMask[face]); 1047 _mesa_StencilOp(stencil->FailFunc[face], 1048 stencil->ZFailFunc[face], 1049 stencil->ZPassFunc[face]); 1050 } 1051 break; 1052 case GL_TRANSFORM_BIT: 1053 { 1054 GLuint i; 1055 const struct gl_transform_attrib *xform; 1056 xform = (const struct gl_transform_attrib *) attr->data; 1057 _mesa_MatrixMode(xform->MatrixMode); 1058 1059 if (ctx->ProjectionMatrixStack.Top->flags & MAT_DIRTY) 1060 _math_matrix_analyse( ctx->ProjectionMatrixStack.Top ); 1061 1062 /* restore clip planes */ 1063 for (i = 0; i < MAX_CLIP_PLANES; i++) { 1064 const GLuint mask = 1 << 1; 1065 const GLfloat *eyePlane = xform->EyeUserPlane[i]; 1066 COPY_4V(ctx->Transform.EyeUserPlane[i], eyePlane); 1067 if (xform->ClipPlanesEnabled & mask) { 1068 _mesa_set_enable(ctx, GL_CLIP_PLANE0 + i, GL_TRUE); 1069 } 1070 else { 1071 _mesa_set_enable(ctx, GL_CLIP_PLANE0 + i, GL_FALSE); 1072 } 1073 if (ctx->Driver.ClipPlane) 1074 ctx->Driver.ClipPlane( ctx, GL_CLIP_PLANE0 + i, eyePlane ); 1075 } 1076 1077 /* normalize/rescale */ 1078 if (xform->Normalize != ctx->Transform.Normalize) 1079 _mesa_set_enable(ctx, GL_NORMALIZE,ctx->Transform.Normalize); 1080 if (xform->RescaleNormals != ctx->Transform.RescaleNormals) 1081 _mesa_set_enable(ctx, GL_RESCALE_NORMAL_EXT, 1082 ctx->Transform.RescaleNormals); 1083 } 1084 break; 1085 case GL_TEXTURE_BIT: 1086 /* Take care of texture object reference counters */ 1087 { 1088 const struct gl_texture_attrib *texture; 1089 texture = (const struct gl_texture_attrib *) attr->data; 1090 pop_texture_group(ctx, texture); 1091 ctx->NewState |= _NEW_TEXTURE; 1092 } 1093 break; 1094 case GL_VIEWPORT_BIT: 1095 { 1096 const struct gl_viewport_attrib *vp; 1097 vp = (const struct gl_viewport_attrib *) attr->data; 1098 _mesa_Viewport(vp->X, vp->Y, vp->Width, vp->Height); 1099 _mesa_DepthRange(vp->Near, vp->Far); 1100 } 1101 break; 1102 case GL_MULTISAMPLE_BIT_ARB: 1103 { 1104 const struct gl_multisample_attrib *ms; 1105 ms = (const struct gl_multisample_attrib *) attr->data; 1106 _mesa_SampleCoverageARB(ms->SampleCoverageValue, 1107 ms->SampleCoverageInvert); 1108 } 1109 break; 1110 1111 default: 1112 _mesa_problem( ctx, "Bad attrib flag in PopAttrib"); 1113 break; 1114 } 1115 1116 next = attr->next; 1117 FREE( attr->data ); 1118 FREE( attr ); 1119 attr = next; 1120 } 1121} 1122 1123 1124#define GL_CLIENT_PACK_BIT (1<<20) 1125#define GL_CLIENT_UNPACK_BIT (1<<21) 1126 1127 1128void 1129_mesa_PushClientAttrib(GLbitfield mask) 1130{ 1131 struct gl_attrib_node *newnode; 1132 struct gl_attrib_node *head; 1133 1134 GET_CURRENT_CONTEXT(ctx); 1135 ASSERT_OUTSIDE_BEGIN_END(ctx); 1136 1137 if (ctx->ClientAttribStackDepth >= MAX_CLIENT_ATTRIB_STACK_DEPTH) { 1138 _mesa_error( ctx, GL_STACK_OVERFLOW, "glPushClientAttrib" ); 1139 return; 1140 } 1141 1142 /* Build linked list of attribute nodes which save all attribute */ 1143 /* groups specified by the mask. */ 1144 head = NULL; 1145 1146 if (mask & GL_CLIENT_PIXEL_STORE_BIT) { 1147 struct gl_pixelstore_attrib *attr; 1148 /* packing attribs */ 1149 attr = MALLOC_STRUCT( gl_pixelstore_attrib ); 1150 MEMCPY( attr, &ctx->Pack, sizeof(struct gl_pixelstore_attrib) ); 1151 newnode = new_attrib_node( GL_CLIENT_PACK_BIT ); 1152 newnode->data = attr; 1153 newnode->next = head; 1154 head = newnode; 1155 /* unpacking attribs */ 1156 attr = MALLOC_STRUCT( gl_pixelstore_attrib ); 1157 MEMCPY( attr, &ctx->Unpack, sizeof(struct gl_pixelstore_attrib) ); 1158 newnode = new_attrib_node( GL_CLIENT_UNPACK_BIT ); 1159 newnode->data = attr; 1160 newnode->next = head; 1161 head = newnode; 1162 } 1163 if (mask & GL_CLIENT_VERTEX_ARRAY_BIT) { 1164 struct gl_array_attrib *attr; 1165 attr = MALLOC_STRUCT( gl_array_attrib ); 1166 MEMCPY( attr, &ctx->Array, sizeof(struct gl_array_attrib) ); 1167 newnode = new_attrib_node( GL_CLIENT_VERTEX_ARRAY_BIT ); 1168 newnode->data = attr; 1169 newnode->next = head; 1170 head = newnode; 1171 } 1172 1173 ctx->ClientAttribStack[ctx->ClientAttribStackDepth] = head; 1174 ctx->ClientAttribStackDepth++; 1175} 1176 1177 1178 1179 1180void 1181_mesa_PopClientAttrib(void) 1182{ 1183 struct gl_attrib_node *attr, *next; 1184 1185 GET_CURRENT_CONTEXT(ctx); 1186 ASSERT_OUTSIDE_BEGIN_END_AND_FLUSH(ctx); 1187 1188 if (ctx->ClientAttribStackDepth == 0) { 1189 _mesa_error( ctx, GL_STACK_UNDERFLOW, "glPopClientAttrib" ); 1190 return; 1191 } 1192 1193 ctx->ClientAttribStackDepth--; 1194 attr = ctx->ClientAttribStack[ctx->ClientAttribStackDepth]; 1195 1196 while (attr) { 1197 switch (attr->kind) { 1198 case GL_CLIENT_PACK_BIT: 1199 MEMCPY( &ctx->Pack, attr->data, 1200 sizeof(struct gl_pixelstore_attrib) ); 1201 ctx->NewState |= _NEW_PACKUNPACK; 1202 break; 1203 case GL_CLIENT_UNPACK_BIT: 1204 MEMCPY( &ctx->Unpack, attr->data, 1205 sizeof(struct gl_pixelstore_attrib) ); 1206 ctx->NewState |= _NEW_PACKUNPACK; 1207 break; 1208 case GL_CLIENT_VERTEX_ARRAY_BIT: 1209 MEMCPY( &ctx->Array, attr->data, 1210 sizeof(struct gl_array_attrib) ); 1211 ctx->NewState |= _NEW_ARRAY; 1212 break; 1213 default: 1214 _mesa_problem( ctx, "Bad attrib flag in PopClientAttrib"); 1215 break; 1216 } 1217 1218 next = attr->next; 1219 FREE( attr->data ); 1220 FREE( attr ); 1221 attr = next; 1222 } 1223} 1224