blob: 881dc0f09354863281d02ad34872d39b98adeb4b [file] [log] [blame]
Brian Paul9560f052000-01-31 23:11:39 +00001/* $Id: context.c,v 1.37 2000/01/31 23:11:39 brianp Exp $ */
jtgafb833d1999-08-19 00:55:39 +00002
3/*
4 * Mesa 3-D graphics library
Brian Paulfbd8f211999-11-11 01:22:25 +00005 * Version: 3.3
jtgafb833d1999-08-19 00:55:39 +00006 *
Brian Paul54287052000-01-17 20:00:15 +00007 * Copyright (C) 1999-2000 Brian Paul All Rights Reserved.
jtgafb833d1999-08-19 00:55:39 +00008 *
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
jtgafb833d1999-08-19 00:55:39 +000028#ifdef PC_HEADER
29#include "all.h"
30#else
Brian Paulfbd8f211999-11-11 01:22:25 +000031#include "glheader.h"
jtgafb833d1999-08-19 00:55:39 +000032#include "accum.h"
33#include "alphabuf.h"
jtgafb833d1999-08-19 00:55:39 +000034#include "clip.h"
35#include "context.h"
36#include "cva.h"
37#include "depth.h"
Brian Paulfbd8f211999-11-11 01:22:25 +000038#include "dispatch.h"
jtgafb833d1999-08-19 00:55:39 +000039#include "dlist.h"
40#include "eval.h"
41#include "enums.h"
Brian Paul585a68c1999-09-11 11:31:34 +000042#include "extensions.h"
jtgafb833d1999-08-19 00:55:39 +000043#include "fog.h"
Brian Paulb7a43041999-11-30 20:34:51 +000044#include "get.h"
Brian Paulfbd8f211999-11-11 01:22:25 +000045#include "glapi.h"
Brian Paulf9b97d92000-01-28 20:17:42 +000046#include "glapinoop.h"
Brian Paul9560f052000-01-31 23:11:39 +000047#include "glthread.h"
jtgafb833d1999-08-19 00:55:39 +000048#include "hash.h"
49#include "light.h"
50#include "lines.h"
51#include "dlist.h"
52#include "macros.h"
53#include "matrix.h"
Brian Paulfbd8f211999-11-11 01:22:25 +000054#include "mem.h"
jtgafb833d1999-08-19 00:55:39 +000055#include "mmath.h"
56#include "pb.h"
57#include "pipeline.h"
58#include "points.h"
jtgafb833d1999-08-19 00:55:39 +000059#include "quads.h"
60#include "shade.h"
61#include "simple_list.h"
62#include "stencil.h"
63#include "stages.h"
64#include "triangle.h"
65#include "translate.h"
66#include "teximage.h"
67#include "texobj.h"
68#include "texstate.h"
69#include "texture.h"
70#include "types.h"
71#include "varray.h"
72#include "vb.h"
73#include "vbcull.h"
74#include "vbfill.h"
75#include "vbrender.h"
76#include "vbxform.h"
Keith Whitwell38756791999-08-29 10:26:31 +000077#include "vertices.h"
jtgafb833d1999-08-19 00:55:39 +000078#include "xform.h"
jtgafb833d1999-08-19 00:55:39 +000079#endif
80
81
82
83/**********************************************************************/
84/***** Context and Thread management *****/
85/**********************************************************************/
86
87
Brian Paul00037781999-12-17 14:52:35 +000088#if !defined(THREADS)
jtgafb833d1999-08-19 00:55:39 +000089
Brian Paul5666c632000-01-18 17:36:16 +000090struct immediate *_mesa_CurrentInput = NULL;
jtgafb833d1999-08-19 00:55:39 +000091
Brian Paul00037781999-12-17 14:52:35 +000092#endif
jtgafb833d1999-08-19 00:55:39 +000093
94
95
96
97/**********************************************************************/
98/***** Profiling functions *****/
99/**********************************************************************/
100
101#ifdef PROFILE
102
103#include <sys/times.h>
104#include <sys/param.h>
105
106
107/*
108 * Return system time in seconds.
109 * NOTE: this implementation may not be very portable!
110 */
111GLdouble gl_time( void )
112{
113 static GLdouble prev_time = 0.0;
114 static GLdouble time;
115 struct tms tm;
116 clock_t clk;
117
118 clk = times(&tm);
119
120#ifdef CLK_TCK
121 time = (double)clk / (double)CLK_TCK;
122#else
123 time = (double)clk / (double)HZ;
124#endif
125
126 if (time>prev_time) {
127 prev_time = time;
128 return time;
129 }
130 else {
131 return prev_time;
132 }
133}
134
135/*
136 * Reset the timing/profiling counters
137 */
138static void init_timings( GLcontext *ctx )
139{
140 ctx->BeginEndCount = 0;
141 ctx->BeginEndTime = 0.0;
142 ctx->VertexCount = 0;
143 ctx->VertexTime = 0.0;
144 ctx->PointCount = 0;
145 ctx->PointTime = 0.0;
146 ctx->LineCount = 0;
147 ctx->LineTime = 0.0;
148 ctx->PolygonCount = 0;
149 ctx->PolygonTime = 0.0;
150 ctx->ClearCount = 0;
151 ctx->ClearTime = 0.0;
152 ctx->SwapCount = 0;
153 ctx->SwapTime = 0.0;
154}
155
156
157/*
158 * Print the accumulated timing/profiling data.
159 */
160static void print_timings( GLcontext *ctx )
161{
162 GLdouble beginendrate;
163 GLdouble vertexrate;
164 GLdouble pointrate;
165 GLdouble linerate;
166 GLdouble polygonrate;
167 GLdouble overhead;
168 GLdouble clearrate;
169 GLdouble swaprate;
170 GLdouble avgvertices;
171
172 if (ctx->BeginEndTime>0.0) {
173 beginendrate = ctx->BeginEndCount / ctx->BeginEndTime;
174 }
175 else {
176 beginendrate = 0.0;
177 }
178 if (ctx->VertexTime>0.0) {
179 vertexrate = ctx->VertexCount / ctx->VertexTime;
180 }
181 else {
182 vertexrate = 0.0;
183 }
184 if (ctx->PointTime>0.0) {
185 pointrate = ctx->PointCount / ctx->PointTime;
186 }
187 else {
188 pointrate = 0.0;
189 }
190 if (ctx->LineTime>0.0) {
191 linerate = ctx->LineCount / ctx->LineTime;
192 }
193 else {
194 linerate = 0.0;
195 }
196 if (ctx->PolygonTime>0.0) {
197 polygonrate = ctx->PolygonCount / ctx->PolygonTime;
198 }
199 else {
200 polygonrate = 0.0;
201 }
202 if (ctx->ClearTime>0.0) {
203 clearrate = ctx->ClearCount / ctx->ClearTime;
204 }
205 else {
206 clearrate = 0.0;
207 }
208 if (ctx->SwapTime>0.0) {
209 swaprate = ctx->SwapCount / ctx->SwapTime;
210 }
211 else {
212 swaprate = 0.0;
213 }
214
215 if (ctx->BeginEndCount>0) {
216 avgvertices = (GLdouble) ctx->VertexCount / (GLdouble) ctx->BeginEndCount;
217 }
218 else {
219 avgvertices = 0.0;
220 }
221
222 overhead = ctx->BeginEndTime - ctx->VertexTime - ctx->PointTime
223 - ctx->LineTime - ctx->PolygonTime;
224
225
226 printf(" Count Time (s) Rate (/s) \n");
227 printf("--------------------------------------------------------\n");
228 printf("glBegin/glEnd %7d %8.3f %10.3f\n",
229 ctx->BeginEndCount, ctx->BeginEndTime, beginendrate);
230 printf(" vertexes transformed %7d %8.3f %10.3f\n",
231 ctx->VertexCount, ctx->VertexTime, vertexrate );
232 printf(" points rasterized %7d %8.3f %10.3f\n",
233 ctx->PointCount, ctx->PointTime, pointrate );
234 printf(" lines rasterized %7d %8.3f %10.3f\n",
235 ctx->LineCount, ctx->LineTime, linerate );
236 printf(" polygons rasterized %7d %8.3f %10.3f\n",
237 ctx->PolygonCount, ctx->PolygonTime, polygonrate );
238 printf(" overhead %8.3f\n", overhead );
239 printf("glClear %7d %8.3f %10.3f\n",
240 ctx->ClearCount, ctx->ClearTime, clearrate );
241 printf("SwapBuffers %7d %8.3f %10.3f\n",
242 ctx->SwapCount, ctx->SwapTime, swaprate );
243 printf("\n");
244
245 printf("Average number of vertices per begin/end: %8.3f\n", avgvertices );
246}
247#endif
248
249
250
251
252
253/**********************************************************************/
Brian Paul4d053dd2000-01-14 04:45:47 +0000254/***** GL Visual allocation/destruction *****/
255/**********************************************************************/
256
257
258/*
259 * Allocate a new GLvisual object.
260 * Input: rgbFlag - GL_TRUE=RGB(A) mode, GL_FALSE=Color Index mode
261 * alphaFlag - alloc software alpha buffers?
262 * dbFlag - double buffering?
263 * stereoFlag - stereo buffer?
264 * depthFits - requested minimum bits per depth buffer value
265 * stencilFits - requested minimum bits per stencil buffer value
266 * accumFits - requested minimum bits per accum buffer component
267 * indexFits - number of bits per pixel if rgbFlag==GL_FALSE
268 * red/green/blue/alphaFits - number of bits per color component
269 * in frame buffer for RGB(A) mode.
270 * Return: pointer to new GLvisual or NULL if requested parameters can't
271 * be met.
272 */
273GLvisual *gl_create_visual( GLboolean rgbFlag,
274 GLboolean alphaFlag,
275 GLboolean dbFlag,
276 GLboolean stereoFlag,
277 GLint depthBits,
278 GLint stencilBits,
279 GLint accumBits,
280 GLint indexBits,
281 GLint redBits,
282 GLint greenBits,
283 GLint blueBits,
284 GLint alphaBits )
285{
286 GLvisual *vis;
287
288 if (depthBits > (GLint) (8*sizeof(GLdepth))) {
289 /* can't meet depth buffer requirements */
290 return NULL;
291 }
292 if (stencilBits > (GLint) (8*sizeof(GLstencil))) {
293 /* can't meet stencil buffer requirements */
294 return NULL;
295 }
296 if (accumBits > (GLint) (8*sizeof(GLaccum))) {
297 /* can't meet accum buffer requirements */
298 return NULL;
299 }
300
301 vis = (GLvisual *) CALLOC( sizeof(GLvisual) );
302 if (!vis) {
303 return NULL;
304 }
305
306 vis->RGBAflag = rgbFlag;
307 vis->DBflag = dbFlag;
308 vis->StereoFlag = stereoFlag;
309 vis->RedBits = redBits;
310 vis->GreenBits = greenBits;
311 vis->BlueBits = blueBits;
312 vis->AlphaBits = alphaFlag ? 8*sizeof(GLubyte) : alphaBits;
313
314 vis->IndexBits = indexBits;
315 vis->DepthBits = (depthBits>0) ? 8*sizeof(GLdepth) : 0;
316 vis->AccumBits = (accumBits>0) ? 8*sizeof(GLaccum) : 0;
317 vis->StencilBits = (stencilBits>0) ? 8*sizeof(GLstencil) : 0;
318
319 vis->SoftwareAlpha = alphaFlag;
320
321 return vis;
322}
323
324
325
326void gl_destroy_visual( GLvisual *vis )
327{
328 FREE( vis );
329}
330
331
332
333/**********************************************************************/
334/***** GL Framebuffer allocation/destruction *****/
335/**********************************************************************/
336
337
338/*
339 * Create a new framebuffer. A GLframebuffer is a struct which
340 * encapsulates the depth, stencil and accum buffers and related
341 * parameters.
342 * Input: visual - a GLvisual pointer
343 * softwareDepth - create/use a software depth buffer?
344 * softwareStencil - create/use a software stencil buffer?
345 * softwareAccum - create/use a software accum buffer?
346 * softwareAlpha - create/use a software alpha buffer?
347
348 * Return: pointer to new GLframebuffer struct or NULL if error.
349 */
350GLframebuffer *gl_create_framebuffer( GLvisual *visual,
351 GLboolean softwareDepth,
352 GLboolean softwareStencil,
353 GLboolean softwareAccum,
354 GLboolean softwareAlpha )
355{
356 GLframebuffer *buffer;
357
358 buffer = CALLOC_STRUCT(gl_frame_buffer);
359 if (!buffer) {
360 return NULL;
361 }
362
363 /* sanity checks */
364 if (softwareDepth ) {
365 assert(visual->DepthBits > 0);
366 }
367 if (softwareStencil) {
368 assert(visual->StencilBits > 0);
369 }
370 if (softwareAccum) {
371 assert(visual->RGBAflag);
372 assert(visual->AccumBits > 0);
373 }
374 if (softwareAlpha) {
375 assert(visual->RGBAflag);
376 assert(visual->AlphaBits > 0);
377 }
378
379 buffer->Visual = visual;
380 buffer->UseSoftwareDepthBuffer = softwareDepth;
381 buffer->UseSoftwareStencilBuffer = softwareStencil;
382 buffer->UseSoftwareAccumBuffer = softwareAccum;
383 buffer->UseSoftwareAlphaBuffers = softwareAlpha;
384
385 return buffer;
386}
387
388
389
390/*
391 * Free a framebuffer struct and its buffers.
392 */
393void gl_destroy_framebuffer( GLframebuffer *buffer )
394{
395 if (buffer) {
396 if (buffer->Depth) {
397 FREE( buffer->Depth );
398 }
399 if (buffer->Accum) {
400 FREE( buffer->Accum );
401 }
402 if (buffer->Stencil) {
403 FREE( buffer->Stencil );
404 }
405 if (buffer->FrontLeftAlpha) {
406 FREE( buffer->FrontLeftAlpha );
407 }
408 if (buffer->BackLeftAlpha) {
409 FREE( buffer->BackLeftAlpha );
410 }
411 if (buffer->FrontRightAlpha) {
412 FREE( buffer->FrontRightAlpha );
413 }
414 if (buffer->BackRightAlpha) {
415 FREE( buffer->BackRightAlpha );
416 }
417 FREE(buffer);
418 }
419}
420
421
422
423/**********************************************************************/
jtgafb833d1999-08-19 00:55:39 +0000424/***** Context allocation, initialization, destroying *****/
425/**********************************************************************/
426
427
Brian Paul9560f052000-01-31 23:11:39 +0000428_glthread_DECLARE_STATIC_MUTEX(OneTimeLock);
429
430
jtgafb833d1999-08-19 00:55:39 +0000431/*
432 * This function just calls all the various one-time-init functions in Mesa.
433 */
434static void one_time_init( void )
435{
436 static GLboolean alreadyCalled = GL_FALSE;
Brian Paul9560f052000-01-31 23:11:39 +0000437 _glthread_LOCK_MUTEX(OneTimeLock);
jtgafb833d1999-08-19 00:55:39 +0000438 if (!alreadyCalled) {
Brian Paul4d053dd2000-01-14 04:45:47 +0000439 /* do some implementation tests */
440 assert( sizeof(GLbyte) == 1 );
441 assert( sizeof(GLshort) >= 2 );
442 assert( sizeof(GLint) >= 4 );
443 assert( sizeof(GLubyte) == 1 );
444 assert( sizeof(GLushort) >= 2 );
445 assert( sizeof(GLuint) >= 4 );
446
jtgafb833d1999-08-19 00:55:39 +0000447 gl_init_clip();
448 gl_init_eval();
449 gl_init_fog();
450 gl_init_math();
451 gl_init_lists();
452 gl_init_shade();
453 gl_init_texture();
454 gl_init_transformation();
455 gl_init_translate();
456 gl_init_vbrender();
457 gl_init_vbxform();
Keith Whitwell38756791999-08-29 10:26:31 +0000458 gl_init_vertices();
Brian Paul68ee4bc2000-01-28 19:02:22 +0000459
460 if (getenv("MESA_DEBUG")) {
461 _glapi_noop_enable_warnings(GL_TRUE);
462 }
463 else {
464 _glapi_noop_enable_warnings(GL_FALSE);
465 }
466
jtgafb833d1999-08-19 00:55:39 +0000467#if defined(DEBUG) && defined(__DATE__) && defined(__TIME__)
468 fprintf(stderr, "Mesa DEBUG build %s %s\n", __DATE__, __TIME__);
469#endif
Brian Paul68ee4bc2000-01-28 19:02:22 +0000470
471 alreadyCalled = GL_TRUE;
472 }
Brian Paul9560f052000-01-31 23:11:39 +0000473 _glthread_UNLOCK_MUTEX(OneTimeLock);
jtgafb833d1999-08-19 00:55:39 +0000474}
475
476
Brian Paul4d053dd2000-01-14 04:45:47 +0000477
jtgafb833d1999-08-19 00:55:39 +0000478/*
479 * Allocate and initialize a shared context state structure.
480 */
481static struct gl_shared_state *alloc_shared_state( void )
482{
Brian Paul6e6d4c61999-10-09 20:17:07 +0000483 GLuint d;
jtgafb833d1999-08-19 00:55:39 +0000484 struct gl_shared_state *ss;
485 GLboolean outOfMemory;
486
Brian Paulbd5cdaf1999-10-13 18:42:49 +0000487 ss = CALLOC_STRUCT(gl_shared_state);
jtgafb833d1999-08-19 00:55:39 +0000488 if (!ss)
489 return NULL;
490
Brian Paulbb797902000-01-24 16:19:54 +0000491 ss->DisplayList = _mesa_NewHashTable();
jtgafb833d1999-08-19 00:55:39 +0000492
Brian Paulbb797902000-01-24 16:19:54 +0000493 ss->TexObjects = _mesa_NewHashTable();
jtgafb833d1999-08-19 00:55:39 +0000494
495 /* Default Texture objects */
496 outOfMemory = GL_FALSE;
Brian Paul6e6d4c61999-10-09 20:17:07 +0000497 for (d = 1 ; d <= 3 ; d++) {
498 ss->DefaultD[d] = gl_alloc_texture_object(ss, 0, d);
499 if (!ss->DefaultD[d]) {
500 outOfMemory = GL_TRUE;
501 break;
jtgafb833d1999-08-19 00:55:39 +0000502 }
Brian Paul6e6d4c61999-10-09 20:17:07 +0000503 ss->DefaultD[d]->RefCount++; /* don't free if not in use */
jtgafb833d1999-08-19 00:55:39 +0000504 }
505
506 if (!ss->DisplayList || !ss->TexObjects || outOfMemory) {
507 /* Ran out of memory at some point. Free everything and return NULL */
508 if (ss->DisplayList)
Brian Paulbb797902000-01-24 16:19:54 +0000509 _mesa_DeleteHashTable(ss->DisplayList);
jtgafb833d1999-08-19 00:55:39 +0000510 if (ss->TexObjects)
Brian Paulbb797902000-01-24 16:19:54 +0000511 _mesa_DeleteHashTable(ss->TexObjects);
Brian Paul6e6d4c61999-10-09 20:17:07 +0000512 if (ss->DefaultD[1])
513 gl_free_texture_object(ss, ss->DefaultD[1]);
514 if (ss->DefaultD[2])
515 gl_free_texture_object(ss, ss->DefaultD[2]);
516 if (ss->DefaultD[3])
517 gl_free_texture_object(ss, ss->DefaultD[3]);
Brian Paulbd5cdaf1999-10-13 18:42:49 +0000518 FREE(ss);
jtgafb833d1999-08-19 00:55:39 +0000519 return NULL;
520 }
521 else {
522 return ss;
523 }
524}
525
526
527/*
528 * Deallocate a shared state context and all children structures.
529 */
530static void free_shared_state( GLcontext *ctx, struct gl_shared_state *ss )
531{
532 /* Free display lists */
533 while (1) {
Brian Paulbb797902000-01-24 16:19:54 +0000534 GLuint list = _mesa_HashFirstEntry(ss->DisplayList);
jtgafb833d1999-08-19 00:55:39 +0000535 if (list) {
536 gl_destroy_list(ctx, list);
537 }
538 else {
539 break;
540 }
541 }
Brian Paulbb797902000-01-24 16:19:54 +0000542 _mesa_DeleteHashTable(ss->DisplayList);
jtgafb833d1999-08-19 00:55:39 +0000543
544 /* Free texture objects */
545 while (ss->TexObjectList)
546 {
547 if (ctx->Driver.DeleteTexture)
548 (*ctx->Driver.DeleteTexture)( ctx, ss->TexObjectList );
549 /* this function removes from linked list too! */
550 gl_free_texture_object(ss, ss->TexObjectList);
551 }
Brian Paulbb797902000-01-24 16:19:54 +0000552 _mesa_DeleteHashTable(ss->TexObjects);
jtgafb833d1999-08-19 00:55:39 +0000553
Brian Paulbd5cdaf1999-10-13 18:42:49 +0000554 FREE(ss);
jtgafb833d1999-08-19 00:55:39 +0000555}
556
557
558
jtgafb833d1999-08-19 00:55:39 +0000559/*
560 * Initialize the nth light. Note that the defaults for light 0 are
561 * different than the other lights.
562 */
563static void init_light( struct gl_light *l, GLuint n )
564{
565 make_empty_list( l );
566
567 ASSIGN_4V( l->Ambient, 0.0, 0.0, 0.0, 1.0 );
568 if (n==0) {
569 ASSIGN_4V( l->Diffuse, 1.0, 1.0, 1.0, 1.0 );
570 ASSIGN_4V( l->Specular, 1.0, 1.0, 1.0, 1.0 );
571 }
572 else {
573 ASSIGN_4V( l->Diffuse, 0.0, 0.0, 0.0, 1.0 );
574 ASSIGN_4V( l->Specular, 0.0, 0.0, 0.0, 1.0 );
575 }
576 ASSIGN_4V( l->EyePosition, 0.0, 0.0, 1.0, 0.0 );
577 ASSIGN_3V( l->EyeDirection, 0.0, 0.0, -1.0 );
578 l->SpotExponent = 0.0;
579 gl_compute_spot_exp_table( l );
580 l->SpotCutoff = 180.0;
581 l->CosCutoff = 0.0; /* KW: -ve values not admitted */
582 l->ConstantAttenuation = 1.0;
583 l->LinearAttenuation = 0.0;
584 l->QuadraticAttenuation = 0.0;
585 l->Enabled = GL_FALSE;
586}
587
588
589
590static void init_lightmodel( struct gl_lightmodel *lm )
591{
592 ASSIGN_4V( lm->Ambient, 0.2, 0.2, 0.2, 1.0 );
593 lm->LocalViewer = GL_FALSE;
594 lm->TwoSide = GL_FALSE;
595 lm->ColorControl = GL_SINGLE_COLOR;
596}
597
598
599static void init_material( struct gl_material *m )
600{
601 ASSIGN_4V( m->Ambient, 0.2, 0.2, 0.2, 1.0 );
602 ASSIGN_4V( m->Diffuse, 0.8, 0.8, 0.8, 1.0 );
603 ASSIGN_4V( m->Specular, 0.0, 0.0, 0.0, 1.0 );
604 ASSIGN_4V( m->Emission, 0.0, 0.0, 0.0, 1.0 );
605 m->Shininess = 0.0;
606 m->AmbientIndex = 0;
607 m->DiffuseIndex = 1;
608 m->SpecularIndex = 1;
609}
610
611
612
613static void init_texture_unit( GLcontext *ctx, GLuint unit )
614{
615 struct gl_texture_unit *texUnit = &ctx->Texture.Unit[unit];
616
617 texUnit->EnvMode = GL_MODULATE;
618 ASSIGN_4V( texUnit->EnvColor, 0.0, 0.0, 0.0, 0.0 );
619 texUnit->TexGenEnabled = 0;
620 texUnit->GenModeS = GL_EYE_LINEAR;
621 texUnit->GenModeT = GL_EYE_LINEAR;
622 texUnit->GenModeR = GL_EYE_LINEAR;
623 texUnit->GenModeQ = GL_EYE_LINEAR;
624 /* Yes, these plane coefficients are correct! */
625 ASSIGN_4V( texUnit->ObjectPlaneS, 1.0, 0.0, 0.0, 0.0 );
626 ASSIGN_4V( texUnit->ObjectPlaneT, 0.0, 1.0, 0.0, 0.0 );
627 ASSIGN_4V( texUnit->ObjectPlaneR, 0.0, 0.0, 0.0, 0.0 );
628 ASSIGN_4V( texUnit->ObjectPlaneQ, 0.0, 0.0, 0.0, 0.0 );
629 ASSIGN_4V( texUnit->EyePlaneS, 1.0, 0.0, 0.0, 0.0 );
630 ASSIGN_4V( texUnit->EyePlaneT, 0.0, 1.0, 0.0, 0.0 );
631 ASSIGN_4V( texUnit->EyePlaneR, 0.0, 0.0, 0.0, 0.0 );
632 ASSIGN_4V( texUnit->EyePlaneQ, 0.0, 0.0, 0.0, 0.0 );
633
Brian Paul6e6d4c61999-10-09 20:17:07 +0000634 texUnit->CurrentD[1] = ctx->Shared->DefaultD[1];
635 texUnit->CurrentD[2] = ctx->Shared->DefaultD[2];
636 texUnit->CurrentD[3] = ctx->Shared->DefaultD[3];
jtgafb833d1999-08-19 00:55:39 +0000637}
638
639
640static void init_fallback_arrays( GLcontext *ctx )
641{
642 struct gl_client_array *cl;
643 GLuint i;
644
645 cl = &ctx->Fallback.Normal;
646 cl->Size = 3;
647 cl->Type = GL_FLOAT;
648 cl->Stride = 0;
649 cl->StrideB = 0;
650 cl->Ptr = (void *) ctx->Current.Normal;
651 cl->Enabled = 1;
652
653 cl = &ctx->Fallback.Color;
654 cl->Size = 4;
655 cl->Type = GL_UNSIGNED_BYTE;
656 cl->Stride = 0;
657 cl->StrideB = 0;
658 cl->Ptr = (void *) ctx->Current.ByteColor;
659 cl->Enabled = 1;
660
661 cl = &ctx->Fallback.Index;
662 cl->Size = 1;
663 cl->Type = GL_UNSIGNED_INT;
664 cl->Stride = 0;
665 cl->StrideB = 0;
666 cl->Ptr = (void *) &ctx->Current.Index;
667 cl->Enabled = 1;
668
669 for (i = 0 ; i < MAX_TEXTURE_UNITS ; i++) {
670 cl = &ctx->Fallback.TexCoord[i];
671 cl->Size = 4;
672 cl->Type = GL_FLOAT;
673 cl->Stride = 0;
674 cl->StrideB = 0;
675 cl->Ptr = (void *) ctx->Current.Texcoord[i];
676 cl->Enabled = 1;
677 }
678
679 cl = &ctx->Fallback.EdgeFlag;
680 cl->Size = 1;
681 cl->Type = GL_UNSIGNED_BYTE;
682 cl->Stride = 0;
683 cl->StrideB = 0;
684 cl->Ptr = (void *) &ctx->Current.EdgeFlag;
685 cl->Enabled = 1;
686}
687
Brian Paul4d053dd2000-01-14 04:45:47 +0000688
jtgafb833d1999-08-19 00:55:39 +0000689/* Initialize a 1-D evaluator map */
690static void init_1d_map( struct gl_1d_map *map, int n, const float *initial )
691{
692 map->Order = 1;
693 map->u1 = 0.0;
694 map->u2 = 1.0;
Brian Paulbd5cdaf1999-10-13 18:42:49 +0000695 map->Points = (GLfloat *) MALLOC(n * sizeof(GLfloat));
jtgafb833d1999-08-19 00:55:39 +0000696 if (map->Points) {
697 GLint i;
698 for (i=0;i<n;i++)
699 map->Points[i] = initial[i];
700 }
jtgafb833d1999-08-19 00:55:39 +0000701}
702
703
704/* Initialize a 2-D evaluator map */
705static void init_2d_map( struct gl_2d_map *map, int n, const float *initial )
706{
707 map->Uorder = 1;
708 map->Vorder = 1;
709 map->u1 = 0.0;
710 map->u2 = 1.0;
711 map->v1 = 0.0;
712 map->v2 = 1.0;
Brian Paulbd5cdaf1999-10-13 18:42:49 +0000713 map->Points = (GLfloat *) MALLOC(n * sizeof(GLfloat));
jtgafb833d1999-08-19 00:55:39 +0000714 if (map->Points) {
715 GLint i;
716 for (i=0;i<n;i++)
717 map->Points[i] = initial[i];
718 }
jtgafb833d1999-08-19 00:55:39 +0000719}
720
721
Brian Paulf0dee651999-11-19 22:51:29 +0000722static void init_color_table( struct gl_color_table *p )
Brian Paulfbd8f211999-11-11 01:22:25 +0000723{
724 p->Table[0] = 255;
725 p->Table[1] = 255;
726 p->Table[2] = 255;
727 p->Table[3] = 255;
728 p->Size = 1;
729 p->IntFormat = GL_RGBA;
730 p->Format = GL_RGBA;
731}
732
jtgafb833d1999-08-19 00:55:39 +0000733
734/*
Brian Paul4d053dd2000-01-14 04:45:47 +0000735 * Initialize the attribute groups in a GLcontext.
jtgafb833d1999-08-19 00:55:39 +0000736 */
Brian Paul4d053dd2000-01-14 04:45:47 +0000737static void init_attrib_groups( GLcontext *ctx )
jtgafb833d1999-08-19 00:55:39 +0000738{
739 GLuint i, j;
740
Brian Paul4d053dd2000-01-14 04:45:47 +0000741 assert(ctx);
jtgafb833d1999-08-19 00:55:39 +0000742
Brian Paul4d053dd2000-01-14 04:45:47 +0000743 /* Constants, may be overriden by device driver */
744 ctx->Const.MaxTextureLevels = MAX_TEXTURE_LEVELS;
745 ctx->Const.MaxTextureSize = 1 << (MAX_TEXTURE_LEVELS - 1);
746 ctx->Const.MaxTextureUnits = MAX_TEXTURE_UNITS;
747 ctx->Const.MaxArrayLockSize = MAX_ARRAY_LOCK_SIZE;
jtgafb833d1999-08-19 00:55:39 +0000748
Brian Paul4d053dd2000-01-14 04:45:47 +0000749 /* Modelview matrix */
750 gl_matrix_ctr( &ctx->ModelView );
751 gl_matrix_alloc_inv( &ctx->ModelView );
752
753 ctx->ModelViewStackDepth = 0;
754 for (i = 0 ; i < MAX_MODELVIEW_STACK_DEPTH ; i++) {
755 gl_matrix_ctr( &ctx->ModelViewStack[i] );
756 gl_matrix_alloc_inv( &ctx->ModelViewStack[i] );
757 }
758
759 /* Projection matrix - need inv for user clipping in clip space*/
760 gl_matrix_ctr( &ctx->ProjectionMatrix );
761 gl_matrix_alloc_inv( &ctx->ProjectionMatrix );
762
763 gl_matrix_ctr( &ctx->ModelProjectMatrix );
764 gl_matrix_ctr( &ctx->ModelProjectWinMatrix );
765 ctx->ModelProjectWinMatrixUptodate = GL_FALSE;
766
767 ctx->ProjectionStackDepth = 0;
768 ctx->NearFarStack[0][0] = 1.0; /* These values seem weird by make */
769 ctx->NearFarStack[0][1] = 0.0; /* sense mathematically. */
770
771 for (i = 0 ; i < MAX_PROJECTION_STACK_DEPTH ; i++) {
772 gl_matrix_ctr( &ctx->ProjectionStack[i] );
773 gl_matrix_alloc_inv( &ctx->ProjectionStack[i] );
774 }
775
776 /* Texture matrix */
777 for (i=0; i<MAX_TEXTURE_UNITS; i++) {
778 gl_matrix_ctr( &ctx->TextureMatrix[i] );
779 ctx->TextureStackDepth[i] = 0;
780 for (j = 0 ; j < MAX_TEXTURE_STACK_DEPTH ; j++) {
781 ctx->TextureStack[i][j].inv = 0;
jtgafb833d1999-08-19 00:55:39 +0000782 }
Brian Paul4d053dd2000-01-14 04:45:47 +0000783 }
jtgafb833d1999-08-19 00:55:39 +0000784
Brian Paul4d053dd2000-01-14 04:45:47 +0000785 /* Accumulate buffer group */
786 ASSIGN_4V( ctx->Accum.ClearColor, 0.0, 0.0, 0.0, 0.0 );
jtgafb833d1999-08-19 00:55:39 +0000787
Brian Paul4d053dd2000-01-14 04:45:47 +0000788 /* Color buffer group */
789 ctx->Color.IndexMask = 0xffffffff;
790 ctx->Color.ColorMask[0] = 0xff;
791 ctx->Color.ColorMask[1] = 0xff;
792 ctx->Color.ColorMask[2] = 0xff;
793 ctx->Color.ColorMask[3] = 0xff;
794 ctx->Color.SWmasking = GL_FALSE;
795 ctx->Color.ClearIndex = 0;
796 ASSIGN_4V( ctx->Color.ClearColor, 0.0, 0.0, 0.0, 0.0 );
797 ctx->Color.DrawBuffer = GL_FRONT;
798 ctx->Color.AlphaEnabled = GL_FALSE;
799 ctx->Color.AlphaFunc = GL_ALWAYS;
800 ctx->Color.AlphaRef = 0;
801 ctx->Color.BlendEnabled = GL_FALSE;
802 ctx->Color.BlendSrcRGB = GL_ONE;
803 ctx->Color.BlendDstRGB = GL_ZERO;
804 ctx->Color.BlendSrcA = GL_ONE;
805 ctx->Color.BlendDstA = GL_ZERO;
806 ctx->Color.BlendEquation = GL_FUNC_ADD_EXT;
807 ctx->Color.BlendFunc = NULL; /* this pointer set only when needed */
808 ASSIGN_4V( ctx->Color.BlendColor, 0.0, 0.0, 0.0, 0.0 );
809 ctx->Color.IndexLogicOpEnabled = GL_FALSE;
810 ctx->Color.ColorLogicOpEnabled = GL_FALSE;
811 ctx->Color.SWLogicOpEnabled = GL_FALSE;
812 ctx->Color.LogicOp = GL_COPY;
813 ctx->Color.DitherFlag = GL_TRUE;
814 ctx->Color.MultiDrawBuffer = GL_FALSE;
jtgafb833d1999-08-19 00:55:39 +0000815
Brian Paul4d053dd2000-01-14 04:45:47 +0000816 /* Current group */
817 ASSIGN_4V( ctx->Current.ByteColor, 255, 255, 255, 255);
818 ctx->Current.Index = 1;
819 for (i=0; i<MAX_TEXTURE_UNITS; i++)
820 ASSIGN_4V( ctx->Current.Texcoord[i], 0.0, 0.0, 0.0, 1.0 );
821 ASSIGN_4V( ctx->Current.RasterPos, 0.0, 0.0, 0.0, 1.0 );
822 ctx->Current.RasterDistance = 0.0;
823 ASSIGN_4V( ctx->Current.RasterColor, 1.0, 1.0, 1.0, 1.0 );
824 ctx->Current.RasterIndex = 1;
825 for (i=0; i<MAX_TEXTURE_UNITS; i++)
826 ASSIGN_4V( ctx->Current.RasterMultiTexCoord[i], 0.0, 0.0, 0.0, 1.0 );
827 ctx->Current.RasterTexCoord = ctx->Current.RasterMultiTexCoord[0];
828 ctx->Current.RasterPosValid = GL_TRUE;
829 ctx->Current.EdgeFlag = GL_TRUE;
830 ASSIGN_3V( ctx->Current.Normal, 0.0, 0.0, 1.0 );
831 ctx->Current.Primitive = (GLenum) (GL_POLYGON + 1);
jtgafb833d1999-08-19 00:55:39 +0000832
Brian Paul4d053dd2000-01-14 04:45:47 +0000833 ctx->Current.Flag = (VERT_NORM|VERT_INDEX|VERT_RGBA|VERT_EDGE|
834 VERT_TEX0_1|VERT_TEX1_1|VERT_MATERIAL);
jtgafb833d1999-08-19 00:55:39 +0000835
Brian Paul4d053dd2000-01-14 04:45:47 +0000836 init_fallback_arrays( ctx );
jtgafb833d1999-08-19 00:55:39 +0000837
Brian Paul4d053dd2000-01-14 04:45:47 +0000838 /* Depth buffer group */
839 ctx->Depth.Test = GL_FALSE;
840 ctx->Depth.Clear = 1.0;
841 ctx->Depth.Func = GL_LESS;
842 ctx->Depth.Mask = GL_TRUE;
jtgafb833d1999-08-19 00:55:39 +0000843
Brian Paul4d053dd2000-01-14 04:45:47 +0000844 /* Evaluators group */
845 ctx->Eval.Map1Color4 = GL_FALSE;
846 ctx->Eval.Map1Index = GL_FALSE;
847 ctx->Eval.Map1Normal = GL_FALSE;
848 ctx->Eval.Map1TextureCoord1 = GL_FALSE;
849 ctx->Eval.Map1TextureCoord2 = GL_FALSE;
850 ctx->Eval.Map1TextureCoord3 = GL_FALSE;
851 ctx->Eval.Map1TextureCoord4 = GL_FALSE;
852 ctx->Eval.Map1Vertex3 = GL_FALSE;
853 ctx->Eval.Map1Vertex4 = GL_FALSE;
854 ctx->Eval.Map2Color4 = GL_FALSE;
855 ctx->Eval.Map2Index = GL_FALSE;
856 ctx->Eval.Map2Normal = GL_FALSE;
857 ctx->Eval.Map2TextureCoord1 = GL_FALSE;
858 ctx->Eval.Map2TextureCoord2 = GL_FALSE;
859 ctx->Eval.Map2TextureCoord3 = GL_FALSE;
860 ctx->Eval.Map2TextureCoord4 = GL_FALSE;
861 ctx->Eval.Map2Vertex3 = GL_FALSE;
862 ctx->Eval.Map2Vertex4 = GL_FALSE;
863 ctx->Eval.AutoNormal = GL_FALSE;
864 ctx->Eval.MapGrid1un = 1;
865 ctx->Eval.MapGrid1u1 = 0.0;
866 ctx->Eval.MapGrid1u2 = 1.0;
867 ctx->Eval.MapGrid2un = 1;
868 ctx->Eval.MapGrid2vn = 1;
869 ctx->Eval.MapGrid2u1 = 0.0;
870 ctx->Eval.MapGrid2u2 = 1.0;
871 ctx->Eval.MapGrid2v1 = 0.0;
872 ctx->Eval.MapGrid2v2 = 1.0;
jtgafb833d1999-08-19 00:55:39 +0000873
Brian Paul4d053dd2000-01-14 04:45:47 +0000874 /* Evaluator data */
875 {
876 static GLfloat vertex[4] = { 0.0, 0.0, 0.0, 1.0 };
877 static GLfloat normal[3] = { 0.0, 0.0, 1.0 };
878 static GLfloat index[1] = { 1.0 };
879 static GLfloat color[4] = { 1.0, 1.0, 1.0, 1.0 };
880 static GLfloat texcoord[4] = { 0.0, 0.0, 0.0, 1.0 };
jtgafb833d1999-08-19 00:55:39 +0000881
Brian Paul4d053dd2000-01-14 04:45:47 +0000882 init_1d_map( &ctx->EvalMap.Map1Vertex3, 3, vertex );
883 init_1d_map( &ctx->EvalMap.Map1Vertex4, 4, vertex );
884 init_1d_map( &ctx->EvalMap.Map1Index, 1, index );
885 init_1d_map( &ctx->EvalMap.Map1Color4, 4, color );
886 init_1d_map( &ctx->EvalMap.Map1Normal, 3, normal );
887 init_1d_map( &ctx->EvalMap.Map1Texture1, 1, texcoord );
888 init_1d_map( &ctx->EvalMap.Map1Texture2, 2, texcoord );
889 init_1d_map( &ctx->EvalMap.Map1Texture3, 3, texcoord );
890 init_1d_map( &ctx->EvalMap.Map1Texture4, 4, texcoord );
jtgafb833d1999-08-19 00:55:39 +0000891
Brian Paul4d053dd2000-01-14 04:45:47 +0000892 init_2d_map( &ctx->EvalMap.Map2Vertex3, 3, vertex );
893 init_2d_map( &ctx->EvalMap.Map2Vertex4, 4, vertex );
894 init_2d_map( &ctx->EvalMap.Map2Index, 1, index );
895 init_2d_map( &ctx->EvalMap.Map2Color4, 4, color );
896 init_2d_map( &ctx->EvalMap.Map2Normal, 3, normal );
897 init_2d_map( &ctx->EvalMap.Map2Texture1, 1, texcoord );
898 init_2d_map( &ctx->EvalMap.Map2Texture2, 2, texcoord );
899 init_2d_map( &ctx->EvalMap.Map2Texture3, 3, texcoord );
900 init_2d_map( &ctx->EvalMap.Map2Texture4, 4, texcoord );
901 }
jtgafb833d1999-08-19 00:55:39 +0000902
Brian Paul4d053dd2000-01-14 04:45:47 +0000903 /* Fog group */
904 ctx->Fog.Enabled = GL_FALSE;
905 ctx->Fog.Mode = GL_EXP;
906 ASSIGN_4V( ctx->Fog.Color, 0.0, 0.0, 0.0, 0.0 );
907 ctx->Fog.Index = 0.0;
908 ctx->Fog.Density = 1.0;
909 ctx->Fog.Start = 0.0;
910 ctx->Fog.End = 1.0;
jtgafb833d1999-08-19 00:55:39 +0000911
Brian Paul4d053dd2000-01-14 04:45:47 +0000912 /* Hint group */
913 ctx->Hint.PerspectiveCorrection = GL_DONT_CARE;
914 ctx->Hint.PointSmooth = GL_DONT_CARE;
915 ctx->Hint.LineSmooth = GL_DONT_CARE;
916 ctx->Hint.PolygonSmooth = GL_DONT_CARE;
917 ctx->Hint.Fog = GL_DONT_CARE;
jtgafb833d1999-08-19 00:55:39 +0000918
Brian Paul4d053dd2000-01-14 04:45:47 +0000919 ctx->Hint.AllowDrawWin = GL_TRUE;
920 ctx->Hint.AllowDrawSpn = GL_TRUE;
921 ctx->Hint.AllowDrawMem = GL_TRUE;
922 ctx->Hint.StrictLighting = GL_TRUE;
jtgafb833d1999-08-19 00:55:39 +0000923
Brian Paul4d053dd2000-01-14 04:45:47 +0000924 /* Pipeline */
925 gl_pipeline_init( ctx );
926 gl_cva_init( ctx );
jtgafb833d1999-08-19 00:55:39 +0000927
Brian Paul4d053dd2000-01-14 04:45:47 +0000928 /* Extensions */
929 gl_extensions_ctr( ctx );
jtgafb833d1999-08-19 00:55:39 +0000930
Brian Paul4d053dd2000-01-14 04:45:47 +0000931 ctx->AllowVertexCull = CLIP_CULLED_BIT;
jtgafb833d1999-08-19 00:55:39 +0000932
Brian Paul4d053dd2000-01-14 04:45:47 +0000933 /* Lighting group */
934 for (i=0;i<MAX_LIGHTS;i++) {
935 init_light( &ctx->Light.Light[i], i );
936 }
937 make_empty_list( &ctx->Light.EnabledList );
jtgafb833d1999-08-19 00:55:39 +0000938
Brian Paul4d053dd2000-01-14 04:45:47 +0000939 init_lightmodel( &ctx->Light.Model );
940 init_material( &ctx->Light.Material[0] );
941 init_material( &ctx->Light.Material[1] );
942 ctx->Light.ShadeModel = GL_SMOOTH;
943 ctx->Light.Enabled = GL_FALSE;
944 ctx->Light.ColorMaterialFace = GL_FRONT_AND_BACK;
945 ctx->Light.ColorMaterialMode = GL_AMBIENT_AND_DIFFUSE;
946 ctx->Light.ColorMaterialBitmask
947 = gl_material_bitmask( ctx,
948 GL_FRONT_AND_BACK,
949 GL_AMBIENT_AND_DIFFUSE, ~0, 0 );
jtgafb833d1999-08-19 00:55:39 +0000950
Brian Paul4d053dd2000-01-14 04:45:47 +0000951 ctx->Light.ColorMaterialEnabled = GL_FALSE;
jtgafb833d1999-08-19 00:55:39 +0000952
Brian Paul4d053dd2000-01-14 04:45:47 +0000953 /* Lighting miscellaneous */
954 ctx->ShineTabList = MALLOC_STRUCT( gl_shine_tab );
955 make_empty_list( ctx->ShineTabList );
956 for (i = 0 ; i < 10 ; i++) {
957 struct gl_shine_tab *s = MALLOC_STRUCT( gl_shine_tab );
958 s->shininess = -1;
959 s->refcount = 0;
960 insert_at_tail( ctx->ShineTabList, s );
961 }
962 for (i = 0 ; i < 4 ; i++) {
963 ctx->ShineTable[i] = ctx->ShineTabList->prev;
964 ctx->ShineTable[i]->refcount++;
965 }
jtgafb833d1999-08-19 00:55:39 +0000966
jtgafb833d1999-08-19 00:55:39 +0000967
Brian Paul4d053dd2000-01-14 04:45:47 +0000968 /* Line group */
969 ctx->Line.SmoothFlag = GL_FALSE;
970 ctx->Line.StippleFlag = GL_FALSE;
971 ctx->Line.Width = 1.0;
972 ctx->Line.StipplePattern = 0xffff;
973 ctx->Line.StippleFactor = 1;
jtgafb833d1999-08-19 00:55:39 +0000974
Brian Paul4d053dd2000-01-14 04:45:47 +0000975 /* Display List group */
976 ctx->List.ListBase = 0;
jtgafb833d1999-08-19 00:55:39 +0000977
Brian Paul4d053dd2000-01-14 04:45:47 +0000978 /* Pixel group */
979 ctx->Pixel.RedBias = 0.0;
980 ctx->Pixel.RedScale = 1.0;
981 ctx->Pixel.GreenBias = 0.0;
982 ctx->Pixel.GreenScale = 1.0;
983 ctx->Pixel.BlueBias = 0.0;
984 ctx->Pixel.BlueScale = 1.0;
985 ctx->Pixel.AlphaBias = 0.0;
986 ctx->Pixel.AlphaScale = 1.0;
987 ctx->Pixel.ScaleOrBiasRGBA = GL_FALSE;
988 ctx->Pixel.DepthBias = 0.0;
989 ctx->Pixel.DepthScale = 1.0;
990 ctx->Pixel.IndexOffset = 0;
991 ctx->Pixel.IndexShift = 0;
992 ctx->Pixel.ZoomX = 1.0;
993 ctx->Pixel.ZoomY = 1.0;
994 ctx->Pixel.MapColorFlag = GL_FALSE;
995 ctx->Pixel.MapStencilFlag = GL_FALSE;
996 ctx->Pixel.MapStoSsize = 1;
997 ctx->Pixel.MapItoIsize = 1;
998 ctx->Pixel.MapItoRsize = 1;
999 ctx->Pixel.MapItoGsize = 1;
1000 ctx->Pixel.MapItoBsize = 1;
1001 ctx->Pixel.MapItoAsize = 1;
1002 ctx->Pixel.MapRtoRsize = 1;
1003 ctx->Pixel.MapGtoGsize = 1;
1004 ctx->Pixel.MapBtoBsize = 1;
1005 ctx->Pixel.MapAtoAsize = 1;
1006 ctx->Pixel.MapStoS[0] = 0;
1007 ctx->Pixel.MapItoI[0] = 0;
1008 ctx->Pixel.MapItoR[0] = 0.0;
1009 ctx->Pixel.MapItoG[0] = 0.0;
1010 ctx->Pixel.MapItoB[0] = 0.0;
1011 ctx->Pixel.MapItoA[0] = 0.0;
1012 ctx->Pixel.MapItoR8[0] = 0;
1013 ctx->Pixel.MapItoG8[0] = 0;
1014 ctx->Pixel.MapItoB8[0] = 0;
1015 ctx->Pixel.MapItoA8[0] = 0;
1016 ctx->Pixel.MapRtoR[0] = 0.0;
1017 ctx->Pixel.MapGtoG[0] = 0.0;
1018 ctx->Pixel.MapBtoB[0] = 0.0;
1019 ctx->Pixel.MapAtoA[0] = 0.0;
jtgafb833d1999-08-19 00:55:39 +00001020
Brian Paul4d053dd2000-01-14 04:45:47 +00001021 /* Point group */
1022 ctx->Point.SmoothFlag = GL_FALSE;
1023 ctx->Point.Size = 1.0;
1024 ctx->Point.Params[0] = 1.0;
1025 ctx->Point.Params[1] = 0.0;
1026 ctx->Point.Params[2] = 0.0;
1027 ctx->Point.Attenuated = GL_FALSE;
1028 ctx->Point.MinSize = 0.0;
1029 ctx->Point.MaxSize = (GLfloat) MAX_POINT_SIZE;
1030 ctx->Point.Threshold = 1.0;
jtgafb833d1999-08-19 00:55:39 +00001031
Brian Paul4d053dd2000-01-14 04:45:47 +00001032 /* Polygon group */
1033 ctx->Polygon.CullFlag = GL_FALSE;
1034 ctx->Polygon.CullFaceMode = GL_BACK;
1035 ctx->Polygon.FrontFace = GL_CCW;
1036 ctx->Polygon.FrontBit = 0;
1037 ctx->Polygon.FrontMode = GL_FILL;
1038 ctx->Polygon.BackMode = GL_FILL;
1039 ctx->Polygon.Unfilled = GL_FALSE;
1040 ctx->Polygon.SmoothFlag = GL_FALSE;
1041 ctx->Polygon.StippleFlag = GL_FALSE;
1042 ctx->Polygon.OffsetFactor = 0.0F;
1043 ctx->Polygon.OffsetUnits = 0.0F;
1044 ctx->Polygon.OffsetPoint = GL_FALSE;
1045 ctx->Polygon.OffsetLine = GL_FALSE;
1046 ctx->Polygon.OffsetFill = GL_FALSE;
jtgafb833d1999-08-19 00:55:39 +00001047
Brian Paul4d053dd2000-01-14 04:45:47 +00001048 /* Polygon Stipple group */
1049 MEMSET( ctx->PolygonStipple, 0xff, 32*sizeof(GLuint) );
jtgafb833d1999-08-19 00:55:39 +00001050
Brian Paul4d053dd2000-01-14 04:45:47 +00001051 /* Scissor group */
1052 ctx->Scissor.Enabled = GL_FALSE;
1053 ctx->Scissor.X = 0;
1054 ctx->Scissor.Y = 0;
1055 ctx->Scissor.Width = 0;
1056 ctx->Scissor.Height = 0;
jtgafb833d1999-08-19 00:55:39 +00001057
Brian Paul4d053dd2000-01-14 04:45:47 +00001058 /* Stencil group */
1059 ctx->Stencil.Enabled = GL_FALSE;
1060 ctx->Stencil.Function = GL_ALWAYS;
1061 ctx->Stencil.FailFunc = GL_KEEP;
1062 ctx->Stencil.ZPassFunc = GL_KEEP;
1063 ctx->Stencil.ZFailFunc = GL_KEEP;
1064 ctx->Stencil.Ref = 0;
1065 ctx->Stencil.ValueMask = STENCIL_MAX;
1066 ctx->Stencil.Clear = 0;
1067 ctx->Stencil.WriteMask = STENCIL_MAX;
jtgafb833d1999-08-19 00:55:39 +00001068
Brian Paul4d053dd2000-01-14 04:45:47 +00001069 /* Texture group */
1070 ctx->Texture.CurrentUnit = 0; /* multitexture */
1071 ctx->Texture.CurrentTransformUnit = 0; /* multitexture */
1072 ctx->Texture.Enabled = 0;
1073 for (i=0; i<MAX_TEXTURE_UNITS; i++)
1074 init_texture_unit( ctx, i );
1075 init_color_table(&ctx->Texture.Palette);
jtgafb833d1999-08-19 00:55:39 +00001076
Brian Paul4d053dd2000-01-14 04:45:47 +00001077 /* Transformation group */
1078 ctx->Transform.MatrixMode = GL_MODELVIEW;
1079 ctx->Transform.Normalize = GL_FALSE;
1080 ctx->Transform.RescaleNormals = GL_FALSE;
1081 for (i=0;i<MAX_CLIP_PLANES;i++) {
1082 ctx->Transform.ClipEnabled[i] = GL_FALSE;
1083 ASSIGN_4V( ctx->Transform.EyeUserPlane[i], 0.0, 0.0, 0.0, 0.0 );
1084 }
1085 ctx->Transform.AnyClip = GL_FALSE;
jtgafb833d1999-08-19 00:55:39 +00001086
Brian Paul4d053dd2000-01-14 04:45:47 +00001087 /* Viewport group */
1088 ctx->Viewport.X = 0;
1089 ctx->Viewport.Y = 0;
1090 ctx->Viewport.Width = 0;
1091 ctx->Viewport.Height = 0;
1092 ctx->Viewport.Near = 0.0;
1093 ctx->Viewport.Far = 1.0;
1094 gl_matrix_ctr(&ctx->Viewport.WindowMap);
jtgafb833d1999-08-19 00:55:39 +00001095
1096#define Sz 10
1097#define Tz 14
Brian Paul4d053dd2000-01-14 04:45:47 +00001098 ctx->Viewport.WindowMap.m[Sz] = 0.5 * DEPTH_SCALE;
1099 ctx->Viewport.WindowMap.m[Tz] = 0.5 * DEPTH_SCALE;
jtgafb833d1999-08-19 00:55:39 +00001100#undef Sz
1101#undef Tz
1102
Brian Paul4d053dd2000-01-14 04:45:47 +00001103 ctx->Viewport.WindowMap.flags = MAT_FLAG_GENERAL_SCALE|MAT_FLAG_TRANSLATION;
1104 ctx->Viewport.WindowMap.type = MATRIX_3D_NO_ROT;
jtgafb833d1999-08-19 00:55:39 +00001105
Brian Paul4d053dd2000-01-14 04:45:47 +00001106 /* Vertex arrays */
1107 ctx->Array.Vertex.Size = 4;
1108 ctx->Array.Vertex.Type = GL_FLOAT;
1109 ctx->Array.Vertex.Stride = 0;
1110 ctx->Array.Vertex.StrideB = 0;
1111 ctx->Array.Vertex.Ptr = NULL;
1112 ctx->Array.Vertex.Enabled = GL_FALSE;
1113 ctx->Array.Normal.Type = GL_FLOAT;
1114 ctx->Array.Normal.Stride = 0;
1115 ctx->Array.Normal.StrideB = 0;
1116 ctx->Array.Normal.Ptr = NULL;
1117 ctx->Array.Normal.Enabled = GL_FALSE;
1118 ctx->Array.Color.Size = 4;
1119 ctx->Array.Color.Type = GL_FLOAT;
1120 ctx->Array.Color.Stride = 0;
1121 ctx->Array.Color.StrideB = 0;
1122 ctx->Array.Color.Ptr = NULL;
1123 ctx->Array.Color.Enabled = GL_FALSE;
1124 ctx->Array.Index.Type = GL_FLOAT;
1125 ctx->Array.Index.Stride = 0;
1126 ctx->Array.Index.StrideB = 0;
1127 ctx->Array.Index.Ptr = NULL;
1128 ctx->Array.Index.Enabled = GL_FALSE;
1129 for (i = 0; i < MAX_TEXTURE_UNITS; i++) {
1130 ctx->Array.TexCoord[i].Size = 4;
1131 ctx->Array.TexCoord[i].Type = GL_FLOAT;
1132 ctx->Array.TexCoord[i].Stride = 0;
1133 ctx->Array.TexCoord[i].StrideB = 0;
1134 ctx->Array.TexCoord[i].Ptr = NULL;
1135 ctx->Array.TexCoord[i].Enabled = GL_FALSE;
1136 }
1137 ctx->Array.TexCoordInterleaveFactor = 1;
1138 ctx->Array.EdgeFlag.Stride = 0;
1139 ctx->Array.EdgeFlag.StrideB = 0;
1140 ctx->Array.EdgeFlag.Ptr = NULL;
1141 ctx->Array.EdgeFlag.Enabled = GL_FALSE;
1142 ctx->Array.ActiveTexture = 0; /* GL_ARB_multitexture */
1143
1144 /* Pixel transfer */
1145 ctx->Pack.Alignment = 4;
1146 ctx->Pack.RowLength = 0;
1147 ctx->Pack.ImageHeight = 0;
1148 ctx->Pack.SkipPixels = 0;
1149 ctx->Pack.SkipRows = 0;
1150 ctx->Pack.SkipImages = 0;
1151 ctx->Pack.SwapBytes = GL_FALSE;
1152 ctx->Pack.LsbFirst = GL_FALSE;
1153 ctx->Unpack.Alignment = 4;
1154 ctx->Unpack.RowLength = 0;
1155 ctx->Unpack.ImageHeight = 0;
1156 ctx->Unpack.SkipPixels = 0;
1157 ctx->Unpack.SkipRows = 0;
1158 ctx->Unpack.SkipImages = 0;
1159 ctx->Unpack.SwapBytes = GL_FALSE;
1160 ctx->Unpack.LsbFirst = GL_FALSE;
1161
1162 /* Feedback */
1163 ctx->Feedback.Type = GL_2D; /* TODO: verify */
1164 ctx->Feedback.Buffer = NULL;
1165 ctx->Feedback.BufferSize = 0;
1166 ctx->Feedback.Count = 0;
1167
1168 /* Selection/picking */
1169 ctx->Select.Buffer = NULL;
1170 ctx->Select.BufferSize = 0;
1171 ctx->Select.BufferCount = 0;
1172 ctx->Select.Hits = 0;
1173 ctx->Select.NameStackDepth = 0;
1174
1175 /* Optimized Accum buffer */
1176 ctx->IntegerAccumMode = GL_TRUE;
1177 ctx->IntegerAccumScaler = 0.0;
1178
1179 /* Renderer and client attribute stacks */
1180 ctx->AttribStackDepth = 0;
1181 ctx->ClientAttribStackDepth = 0;
1182
1183 /* Miscellaneous */
1184 ctx->NewState = NEW_ALL;
1185 ctx->RenderMode = GL_RENDER;
1186 ctx->StippleCounter = 0;
1187 ctx->NeedNormals = GL_FALSE;
1188 ctx->DoViewportMapping = GL_TRUE;
1189
1190 ctx->NeedEyeCoords = GL_FALSE;
1191 ctx->NeedEyeNormals = GL_FALSE;
1192 ctx->vb_proj_matrix = &ctx->ModelProjectMatrix;
1193
1194 /* Display list */
1195 ctx->CallDepth = 0;
1196 ctx->ExecuteFlag = GL_TRUE;
1197 ctx->CompileFlag = GL_FALSE;
1198 ctx->CurrentListPtr = NULL;
1199 ctx->CurrentBlock = NULL;
1200 ctx->CurrentListNum = 0;
1201 ctx->CurrentPos = 0;
1202
1203 ctx->ErrorValue = (GLenum) GL_NO_ERROR;
1204
1205 ctx->CatchSignals = GL_TRUE;
1206
1207 /* For debug/development only */
1208 ctx->NoRaster = getenv("MESA_NO_RASTER") ? GL_TRUE : GL_FALSE;
1209 ctx->FirstTimeCurrent = GL_TRUE;
1210
1211 /* Dither disable */
1212 ctx->NoDither = getenv("MESA_NO_DITHER") ? GL_TRUE : GL_FALSE;
1213 if (ctx->NoDither) {
1214 if (getenv("MESA_DEBUG")) {
1215 fprintf(stderr, "MESA_NO_DITHER set - dithering disabled\n");
jtgafb833d1999-08-19 00:55:39 +00001216 }
Brian Paul4d053dd2000-01-14 04:45:47 +00001217 ctx->Color.DitherFlag = GL_FALSE;
Brian Paul00037781999-12-17 14:52:35 +00001218 }
1219}
1220
1221
1222
1223
jtgafb833d1999-08-19 00:55:39 +00001224/*
1225 * Allocate the proxy textures. If we run out of memory part way through
1226 * the allocations clean up and return GL_FALSE.
1227 * Return: GL_TRUE=success, GL_FALSE=failure
1228 */
1229static GLboolean alloc_proxy_textures( GLcontext *ctx )
1230{
1231 GLboolean out_of_memory;
1232 GLint i;
1233
1234 ctx->Texture.Proxy1D = gl_alloc_texture_object(NULL, 0, 1);
1235 if (!ctx->Texture.Proxy1D) {
1236 return GL_FALSE;
1237 }
1238
1239 ctx->Texture.Proxy2D = gl_alloc_texture_object(NULL, 0, 2);
1240 if (!ctx->Texture.Proxy2D) {
1241 gl_free_texture_object(NULL, ctx->Texture.Proxy1D);
1242 return GL_FALSE;
1243 }
1244
1245 ctx->Texture.Proxy3D = gl_alloc_texture_object(NULL, 0, 3);
1246 if (!ctx->Texture.Proxy3D) {
1247 gl_free_texture_object(NULL, ctx->Texture.Proxy1D);
1248 gl_free_texture_object(NULL, ctx->Texture.Proxy2D);
1249 return GL_FALSE;
1250 }
1251
1252 out_of_memory = GL_FALSE;
1253 for (i=0;i<MAX_TEXTURE_LEVELS;i++) {
1254 ctx->Texture.Proxy1D->Image[i] = gl_alloc_texture_image();
1255 ctx->Texture.Proxy2D->Image[i] = gl_alloc_texture_image();
1256 ctx->Texture.Proxy3D->Image[i] = gl_alloc_texture_image();
1257 if (!ctx->Texture.Proxy1D->Image[i]
1258 || !ctx->Texture.Proxy2D->Image[i]
1259 || !ctx->Texture.Proxy3D->Image[i]) {
1260 out_of_memory = GL_TRUE;
1261 }
1262 }
1263 if (out_of_memory) {
1264 for (i=0;i<MAX_TEXTURE_LEVELS;i++) {
1265 if (ctx->Texture.Proxy1D->Image[i]) {
1266 gl_free_texture_image(ctx->Texture.Proxy1D->Image[i]);
1267 }
1268 if (ctx->Texture.Proxy2D->Image[i]) {
1269 gl_free_texture_image(ctx->Texture.Proxy2D->Image[i]);
1270 }
1271 if (ctx->Texture.Proxy3D->Image[i]) {
1272 gl_free_texture_image(ctx->Texture.Proxy3D->Image[i]);
1273 }
1274 }
1275 gl_free_texture_object(NULL, ctx->Texture.Proxy1D);
1276 gl_free_texture_object(NULL, ctx->Texture.Proxy2D);
1277 gl_free_texture_object(NULL, ctx->Texture.Proxy3D);
1278 return GL_FALSE;
1279 }
1280 else {
1281 return GL_TRUE;
1282 }
1283}
1284
1285
1286
jtgafb833d1999-08-19 00:55:39 +00001287/*
Brian Paul4d053dd2000-01-14 04:45:47 +00001288 * Initialize a GLcontext struct.
jtgafb833d1999-08-19 00:55:39 +00001289 */
Brian Paul4d053dd2000-01-14 04:45:47 +00001290GLboolean gl_initialize_context_data( GLcontext *ctx,
1291 GLvisual *visual,
1292 GLcontext *share_list,
1293 void *driver_ctx,
1294 GLboolean direct )
jtgafb833d1999-08-19 00:55:39 +00001295{
jtgafb833d1999-08-19 00:55:39 +00001296 (void) direct; /* not used */
1297
jtgafb833d1999-08-19 00:55:39 +00001298 /* misc one-time initializations */
1299 one_time_init();
1300
jtgafb833d1999-08-19 00:55:39 +00001301 ctx->DriverCtx = driver_ctx;
1302 ctx->Visual = visual;
Brian Paul3f02f901999-11-24 18:48:30 +00001303 ctx->DrawBuffer = NULL;
1304 ctx->ReadBuffer = NULL;
jtgafb833d1999-08-19 00:55:39 +00001305
1306 ctx->VB = gl_vb_create_for_immediate( ctx );
1307 if (!ctx->VB) {
Brian Paulbd5cdaf1999-10-13 18:42:49 +00001308 FREE( ctx );
Brian Paul4d053dd2000-01-14 04:45:47 +00001309 return GL_FALSE;
jtgafb833d1999-08-19 00:55:39 +00001310 }
1311 ctx->input = ctx->VB->IM;
1312
1313 ctx->PB = gl_alloc_pb();
1314 if (!ctx->PB) {
Brian Paulbd5cdaf1999-10-13 18:42:49 +00001315 FREE( ctx->VB );
1316 FREE( ctx );
Brian Paul4d053dd2000-01-14 04:45:47 +00001317 return GL_FALSE;
jtgafb833d1999-08-19 00:55:39 +00001318 }
1319
1320 if (share_list) {
1321 /* share the group of display lists of another context */
1322 ctx->Shared = share_list->Shared;
1323 }
1324 else {
1325 /* allocate new group of display lists */
1326 ctx->Shared = alloc_shared_state();
1327 if (!ctx->Shared) {
Brian Paulbd5cdaf1999-10-13 18:42:49 +00001328 FREE(ctx->VB);
1329 FREE(ctx->PB);
1330 FREE(ctx);
Brian Paul4d053dd2000-01-14 04:45:47 +00001331 return GL_FALSE;
jtgafb833d1999-08-19 00:55:39 +00001332 }
1333 }
Brian Paul9560f052000-01-31 23:11:39 +00001334 _glthread_LOCK_MUTEX(ctx->Shared->Mutex);
jtgafb833d1999-08-19 00:55:39 +00001335 ctx->Shared->RefCount++;
Brian Paul9560f052000-01-31 23:11:39 +00001336 _glthread_UNLOCK_MUTEX(ctx->Shared->Mutex);
jtgafb833d1999-08-19 00:55:39 +00001337
Brian Paul4d053dd2000-01-14 04:45:47 +00001338 init_attrib_groups( ctx );
1339
jtgafb833d1999-08-19 00:55:39 +00001340 gl_reset_vb( ctx->VB );
1341 gl_reset_input( ctx );
1342
jtgafb833d1999-08-19 00:55:39 +00001343 if (visual->DBflag) {
1344 ctx->Color.DrawBuffer = GL_BACK;
1345 ctx->Color.DriverDrawBuffer = GL_BACK_LEFT;
1346 ctx->Color.DrawDestMask = BACK_LEFT_BIT;
1347 ctx->Pixel.ReadBuffer = GL_BACK;
1348 ctx->Pixel.DriverReadBuffer = GL_BACK_LEFT;
1349 }
1350 else {
1351 ctx->Color.DrawBuffer = GL_FRONT;
1352 ctx->Color.DriverDrawBuffer = GL_FRONT_LEFT;
1353 ctx->Color.DrawDestMask = FRONT_LEFT_BIT;
1354 ctx->Pixel.ReadBuffer = GL_FRONT;
1355 ctx->Pixel.DriverReadBuffer = GL_FRONT_LEFT;
1356 }
1357
1358#ifdef PROFILE
1359 init_timings( ctx );
1360#endif
1361
jtgafb833d1999-08-19 00:55:39 +00001362 if (!alloc_proxy_textures(ctx)) {
1363 free_shared_state(ctx, ctx->Shared);
Brian Paulbd5cdaf1999-10-13 18:42:49 +00001364 FREE(ctx->VB);
1365 FREE(ctx->PB);
1366 FREE(ctx);
Brian Paul4d053dd2000-01-14 04:45:47 +00001367 return GL_FALSE;
jtgafb833d1999-08-19 00:55:39 +00001368 }
jtgafb833d1999-08-19 00:55:39 +00001369
Brian Paulfbd8f211999-11-11 01:22:25 +00001370 /* setup API dispatch tables */
1371 _mesa_init_exec_table( &ctx->Exec );
1372 _mesa_init_dlist_table( &ctx->Save );
1373 ctx->CurrentDispatch = &ctx->Exec;
jtgafb833d1999-08-19 00:55:39 +00001374
Brian Paul4d053dd2000-01-14 04:45:47 +00001375 return GL_TRUE;
jtgafb833d1999-08-19 00:55:39 +00001376}
1377
jtgafb833d1999-08-19 00:55:39 +00001378
1379
1380/*
Brian Paul4d053dd2000-01-14 04:45:47 +00001381 * Allocate and initialize a GLcontext structure.
1382 * Input: visual - a GLvisual pointer
1383 * sharelist - another context to share display lists with or NULL
1384 * driver_ctx - pointer to device driver's context state struct
1385 * Return: pointer to a new gl_context struct or NULL if error.
1386 */
1387GLcontext *gl_create_context( GLvisual *visual,
1388 GLcontext *share_list,
1389 void *driver_ctx,
1390 GLboolean direct )
1391{
1392 GLcontext *ctx = (GLcontext *) CALLOC( sizeof(GLcontext) );
1393 if (!ctx) {
1394 return NULL;
1395 }
1396
1397 if (gl_initialize_context_data(ctx, visual, share_list,
1398 driver_ctx, direct)) {
1399 return ctx;
1400 }
1401 else {
1402 FREE(ctx);
1403 return NULL;
1404 }
1405}
1406
1407
1408
1409/*
1410 * Free the data associated with the given context.
1411 * But don't free() the GLcontext struct itself!
1412 */
1413void gl_free_context_data( GLcontext *ctx )
1414{
1415 GLuint i;
1416 struct gl_shine_tab *s, *tmps;
1417
1418 /* if we're destroying the current context, unbind it first */
1419 if (ctx == gl_get_current_context()) {
1420 gl_make_current(NULL, NULL);
1421 }
1422
1423#ifdef PROFILE
1424 if (getenv("MESA_PROFILE")) {
1425 print_timings( ctx );
1426 }
1427#endif
1428
1429 gl_matrix_dtr( &ctx->ModelView );
1430 for (i = 0 ; i < MAX_MODELVIEW_STACK_DEPTH ; i++) {
1431 gl_matrix_dtr( &ctx->ModelViewStack[i] );
1432 }
1433 gl_matrix_dtr( &ctx->ProjectionMatrix );
1434 for (i = 0 ; i < MAX_PROJECTION_STACK_DEPTH ; i++) {
1435 gl_matrix_dtr( &ctx->ProjectionStack[i] );
1436 }
1437
1438 FREE( ctx->PB );
1439
1440 if(ctx->input != ctx->VB->IM)
1441 gl_immediate_free( ctx->input );
1442
1443 gl_vb_free( ctx->VB );
1444
Brian Paul9560f052000-01-31 23:11:39 +00001445 _glthread_LOCK_MUTEX(ctx->Shared->Mutex);
Brian Paul4d053dd2000-01-14 04:45:47 +00001446 ctx->Shared->RefCount--;
Brian Paul9560f052000-01-31 23:11:39 +00001447 assert(ctx->Shared->RefCount >= 0);
1448 _glthread_UNLOCK_MUTEX(ctx->Shared->Mutex);
1449 if (ctx->Shared->RefCount == 0) {
Brian Paul4d053dd2000-01-14 04:45:47 +00001450 /* free shared state */
1451 free_shared_state( ctx, ctx->Shared );
1452 }
1453
1454 foreach_s( s, tmps, ctx->ShineTabList ) {
1455 FREE( s );
1456 }
1457 FREE( ctx->ShineTabList );
1458
1459 /* Free proxy texture objects */
1460 gl_free_texture_object( NULL, ctx->Texture.Proxy1D );
1461 gl_free_texture_object( NULL, ctx->Texture.Proxy2D );
1462 gl_free_texture_object( NULL, ctx->Texture.Proxy3D );
1463
1464 /* Free evaluator data */
1465 if (ctx->EvalMap.Map1Vertex3.Points)
1466 FREE( ctx->EvalMap.Map1Vertex3.Points );
1467 if (ctx->EvalMap.Map1Vertex4.Points)
1468 FREE( ctx->EvalMap.Map1Vertex4.Points );
1469 if (ctx->EvalMap.Map1Index.Points)
1470 FREE( ctx->EvalMap.Map1Index.Points );
1471 if (ctx->EvalMap.Map1Color4.Points)
1472 FREE( ctx->EvalMap.Map1Color4.Points );
1473 if (ctx->EvalMap.Map1Normal.Points)
1474 FREE( ctx->EvalMap.Map1Normal.Points );
1475 if (ctx->EvalMap.Map1Texture1.Points)
1476 FREE( ctx->EvalMap.Map1Texture1.Points );
1477 if (ctx->EvalMap.Map1Texture2.Points)
1478 FREE( ctx->EvalMap.Map1Texture2.Points );
1479 if (ctx->EvalMap.Map1Texture3.Points)
1480 FREE( ctx->EvalMap.Map1Texture3.Points );
1481 if (ctx->EvalMap.Map1Texture4.Points)
1482 FREE( ctx->EvalMap.Map1Texture4.Points );
1483
1484 if (ctx->EvalMap.Map2Vertex3.Points)
1485 FREE( ctx->EvalMap.Map2Vertex3.Points );
1486 if (ctx->EvalMap.Map2Vertex4.Points)
1487 FREE( ctx->EvalMap.Map2Vertex4.Points );
1488 if (ctx->EvalMap.Map2Index.Points)
1489 FREE( ctx->EvalMap.Map2Index.Points );
1490 if (ctx->EvalMap.Map2Color4.Points)
1491 FREE( ctx->EvalMap.Map2Color4.Points );
1492 if (ctx->EvalMap.Map2Normal.Points)
1493 FREE( ctx->EvalMap.Map2Normal.Points );
1494 if (ctx->EvalMap.Map2Texture1.Points)
1495 FREE( ctx->EvalMap.Map2Texture1.Points );
1496 if (ctx->EvalMap.Map2Texture2.Points)
1497 FREE( ctx->EvalMap.Map2Texture2.Points );
1498 if (ctx->EvalMap.Map2Texture3.Points)
1499 FREE( ctx->EvalMap.Map2Texture3.Points );
1500 if (ctx->EvalMap.Map2Texture4.Points)
1501 FREE( ctx->EvalMap.Map2Texture4.Points );
1502
1503 /* Free cache of immediate buffers. */
1504 while (ctx->nr_im_queued-- > 0) {
1505 struct immediate * next = ctx->freed_im_queue->next;
1506 FREE( ctx->freed_im_queue );
1507 ctx->freed_im_queue = next;
1508 }
1509 gl_extensions_dtr(ctx);
1510}
1511
1512
1513
1514/*
1515 * Destroy a GLcontext structure.
jtgafb833d1999-08-19 00:55:39 +00001516 */
1517void gl_destroy_context( GLcontext *ctx )
1518{
1519 if (ctx) {
Brian Paul4d053dd2000-01-14 04:45:47 +00001520 gl_free_context_data(ctx);
Brian Paulbd5cdaf1999-10-13 18:42:49 +00001521 FREE( (void *) ctx );
jtgafb833d1999-08-19 00:55:39 +00001522 }
1523}
1524
1525
1526
1527/*
Brian Paul4d053dd2000-01-14 04:45:47 +00001528 * Called by the driver after both the context and driver are fully
1529 * initialized. Currently just reads the config file.
jtgafb833d1999-08-19 00:55:39 +00001530 */
Brian Paul00037781999-12-17 14:52:35 +00001531void gl_context_initialize( GLcontext *ctx )
jtgafb833d1999-08-19 00:55:39 +00001532{
Brian Paul00037781999-12-17 14:52:35 +00001533 gl_read_config_file( ctx );
jtgafb833d1999-08-19 00:55:39 +00001534}
1535
1536
1537
1538/*
1539 * Copy attribute groups from one context to another.
1540 * Input: src - source context
1541 * dst - destination context
1542 * mask - bitwise OR of GL_*_BIT flags
1543 */
1544void gl_copy_context( const GLcontext *src, GLcontext *dst, GLuint mask )
1545{
1546 if (mask & GL_ACCUM_BUFFER_BIT) {
1547 MEMCPY( &dst->Accum, &src->Accum, sizeof(struct gl_accum_attrib) );
1548 }
1549 if (mask & GL_COLOR_BUFFER_BIT) {
1550 MEMCPY( &dst->Color, &src->Color, sizeof(struct gl_colorbuffer_attrib) );
1551 }
1552 if (mask & GL_CURRENT_BIT) {
1553 MEMCPY( &dst->Current, &src->Current, sizeof(struct gl_current_attrib) );
1554 }
1555 if (mask & GL_DEPTH_BUFFER_BIT) {
1556 MEMCPY( &dst->Depth, &src->Depth, sizeof(struct gl_depthbuffer_attrib) );
1557 }
1558 if (mask & GL_ENABLE_BIT) {
1559 /* no op */
1560 }
1561 if (mask & GL_EVAL_BIT) {
1562 MEMCPY( &dst->Eval, &src->Eval, sizeof(struct gl_eval_attrib) );
1563 }
1564 if (mask & GL_FOG_BIT) {
1565 MEMCPY( &dst->Fog, &src->Fog, sizeof(struct gl_fog_attrib) );
1566 }
1567 if (mask & GL_HINT_BIT) {
1568 MEMCPY( &dst->Hint, &src->Hint, sizeof(struct gl_hint_attrib) );
1569 }
1570 if (mask & GL_LIGHTING_BIT) {
1571 MEMCPY( &dst->Light, &src->Light, sizeof(struct gl_light_attrib) );
Brian Paul00037781999-12-17 14:52:35 +00001572 /* gl_reinit_light_attrib( &dst->Light ); */
jtgafb833d1999-08-19 00:55:39 +00001573 }
1574 if (mask & GL_LINE_BIT) {
1575 MEMCPY( &dst->Line, &src->Line, sizeof(struct gl_line_attrib) );
1576 }
1577 if (mask & GL_LIST_BIT) {
1578 MEMCPY( &dst->List, &src->List, sizeof(struct gl_list_attrib) );
1579 }
1580 if (mask & GL_PIXEL_MODE_BIT) {
1581 MEMCPY( &dst->Pixel, &src->Pixel, sizeof(struct gl_pixel_attrib) );
1582 }
1583 if (mask & GL_POINT_BIT) {
1584 MEMCPY( &dst->Point, &src->Point, sizeof(struct gl_point_attrib) );
1585 }
1586 if (mask & GL_POLYGON_BIT) {
1587 MEMCPY( &dst->Polygon, &src->Polygon, sizeof(struct gl_polygon_attrib) );
1588 }
1589 if (mask & GL_POLYGON_STIPPLE_BIT) {
1590 /* Use loop instead of MEMCPY due to problem with Portland Group's
1591 * C compiler. Reported by John Stone.
1592 */
1593 int i;
1594 for (i=0;i<32;i++) {
1595 dst->PolygonStipple[i] = src->PolygonStipple[i];
1596 }
1597 }
1598 if (mask & GL_SCISSOR_BIT) {
1599 MEMCPY( &dst->Scissor, &src->Scissor, sizeof(struct gl_scissor_attrib) );
1600 }
1601 if (mask & GL_STENCIL_BUFFER_BIT) {
1602 MEMCPY( &dst->Stencil, &src->Stencil, sizeof(struct gl_stencil_attrib) );
1603 }
1604 if (mask & GL_TEXTURE_BIT) {
1605 MEMCPY( &dst->Texture, &src->Texture, sizeof(struct gl_texture_attrib) );
1606 }
1607 if (mask & GL_TRANSFORM_BIT) {
1608 MEMCPY( &dst->Transform, &src->Transform, sizeof(struct gl_transform_attrib) );
1609 }
1610 if (mask & GL_VIEWPORT_BIT) {
1611 MEMCPY( &dst->Viewport, &src->Viewport, sizeof(struct gl_viewport_attrib) );
1612 }
1613}
1614
1615
jtgafb833d1999-08-19 00:55:39 +00001616/*
Brian Paul00037781999-12-17 14:52:35 +00001617 * Set the current context, binding the given frame buffer to the context.
1618 */
1619void gl_make_current( GLcontext *newCtx, GLframebuffer *buffer )
1620{
1621 gl_make_current2( newCtx, buffer, buffer );
1622}
1623
1624
1625/*
1626 * Bind the given context to the given draw-buffer and read-buffer
1627 * and make it the current context for this thread.
1628 */
1629void gl_make_current2( GLcontext *newCtx, GLframebuffer *drawBuffer,
1630 GLframebuffer *readBuffer )
1631{
1632#if 0
Brian Paulf9b97d92000-01-28 20:17:42 +00001633 GLcontext *oldCtx = gl_get_context();
Brian Paul00037781999-12-17 14:52:35 +00001634
1635 /* Flush the old context
1636 */
1637 if (oldCtx) {
1638 ASSERT_OUTSIDE_BEGIN_END_AND_FLUSH(oldCtx, "gl_make_current");
1639
1640 /* unbind frame buffers from context */
1641 if (oldCtx->DrawBuffer) {
1642 oldCtx->DrawBuffer = NULL;
1643 }
1644 if (oldCtx->ReadBuffer) {
1645 oldCtx->ReadBuffer = NULL;
1646 }
1647 }
1648#endif
1649
1650 /* We call this function periodically (just here for now) in
1651 * order to detect when multithreading has begun.
1652 */
1653 _glapi_check_multithread();
1654
Brian Paulf9b97d92000-01-28 20:17:42 +00001655 _glapi_set_context((void *) newCtx);
Brian Paul00037781999-12-17 14:52:35 +00001656 ASSERT(gl_get_current_context() == newCtx);
1657 if (newCtx) {
1658 SET_IMMEDIATE(newCtx, newCtx->input);
1659 _glapi_set_dispatch(newCtx->CurrentDispatch);
1660 }
1661 else {
1662 _glapi_set_dispatch(NULL); /* none current */
1663 }
1664
1665 if (MESA_VERBOSE) fprintf(stderr, "gl_make_current()\n");
1666
1667 if (newCtx && drawBuffer && readBuffer) {
1668 /* TODO: check if newCtx and buffer's visual match??? */
1669 newCtx->DrawBuffer = drawBuffer;
1670 newCtx->ReadBuffer = readBuffer;
1671 newCtx->NewState = NEW_ALL; /* just to be safe */
1672 gl_update_state( newCtx );
1673 }
1674
1675 /* We can use this to help debug user's problems. Tell the to set
1676 * the MESA_INFO env variable before running their app. Then the
1677 * first time each context is made current we'll print some useful
1678 * information.
1679 */
1680 if (newCtx && newCtx->FirstTimeCurrent) {
1681 if (getenv("MESA_INFO")) {
1682 fprintf(stderr, "Mesa GL_VERSION = %s\n", (char *) _mesa_GetString(GL_VERSION));
1683 fprintf(stderr, "Mesa GL_RENDERER = %s\n", (char *) _mesa_GetString(GL_RENDERER));
1684 fprintf(stderr, "Mesa GL_VENDOR = %s\n", (char *) _mesa_GetString(GL_VENDOR));
1685 fprintf(stderr, "Mesa GL_EXTENSIONS = %s\n", (char *) _mesa_GetString(GL_EXTENSIONS));
Brian Paul09cb1481999-12-17 17:00:32 +00001686#if defined(THREADS)
1687 fprintf(stderr, "Mesa thread-safe: YES\n");
1688#else
1689 fprintf(stderr, "Mesa thread-safe: NO\n");
1690#endif
Brian Paul54287052000-01-17 20:00:15 +00001691#if defined(USE_X86_ASM)
1692 fprintf(stderr, "Mesa x86-optimized: YES\n");
1693#else
1694 fprintf(stderr, "Mesa x86-optimized: NO\n");
1695#endif
Brian Paul00037781999-12-17 14:52:35 +00001696 }
1697 newCtx->FirstTimeCurrent = GL_FALSE;
1698 }
1699}
1700
1701
1702
1703/*
1704 * Return current context handle for the calling thread.
1705 * This isn't the fastest way to get the current context.
1706 * If you need speed, see the GET_CURRENT_CONTEXT() macro in context.h
1707 */
1708GLcontext *gl_get_current_context( void )
1709{
Brian Paulf9b97d92000-01-28 20:17:42 +00001710 return (GLcontext *) _glapi_get_context();
Brian Paul00037781999-12-17 14:52:35 +00001711}
1712
1713
1714
1715/*
Brian Paulfbd8f211999-11-11 01:22:25 +00001716 * This should be called by device drivers just before they do a
1717 * swapbuffers. Any pending rendering commands will be executed.
jtgafb833d1999-08-19 00:55:39 +00001718 */
Brian Paulfbd8f211999-11-11 01:22:25 +00001719void
1720_mesa_swapbuffers(GLcontext *ctx)
jtgafb833d1999-08-19 00:55:39 +00001721{
Brian Paulfbd8f211999-11-11 01:22:25 +00001722 FLUSH_VB( ctx, "swap buffers" );
jtgafb833d1999-08-19 00:55:39 +00001723}
1724
1725
Brian Paul00037781999-12-17 14:52:35 +00001726
Brian Paulfbd8f211999-11-11 01:22:25 +00001727/*
1728 * Return pointer to this context's current API dispatch table.
1729 * It'll either be the immediate-mode execute dispatcher or the
1730 * display list compile dispatcher.
1731 */
1732struct _glapi_table *
1733_mesa_get_dispatch(GLcontext *ctx)
1734{
1735 return ctx->CurrentDispatch;
1736}
1737
1738
1739
1740void
1741_mesa_ResizeBuffersMESA( void )
1742{
Brian Paul00037781999-12-17 14:52:35 +00001743 GLcontext *ctx = gl_get_current_context();
Brian Paulfbd8f211999-11-11 01:22:25 +00001744
1745 GLuint buf_width, buf_height;
1746
1747 if (MESA_VERBOSE & VERBOSE_API)
1748 fprintf(stderr, "glResizeBuffersMESA\n");
1749
1750 /* ask device driver for size of output buffer */
1751 (*ctx->Driver.GetBufferSize)( ctx, &buf_width, &buf_height );
1752
1753 /* see if size of device driver's color buffer (window) has changed */
Brian Paul3f02f901999-11-24 18:48:30 +00001754 if (ctx->DrawBuffer->Width == (GLint) buf_width &&
1755 ctx->DrawBuffer->Height == (GLint) buf_height)
Brian Paulfbd8f211999-11-11 01:22:25 +00001756 return;
1757
1758 ctx->NewState |= NEW_RASTER_OPS; /* to update scissor / window bounds */
1759
1760 /* save buffer size */
Brian Paul3f02f901999-11-24 18:48:30 +00001761 ctx->DrawBuffer->Width = buf_width;
1762 ctx->DrawBuffer->Height = buf_height;
Brian Paulfbd8f211999-11-11 01:22:25 +00001763
1764 /* Reallocate other buffers if needed. */
Brian Paul5c3bee51999-12-10 19:09:21 +00001765 if (ctx->DrawBuffer->UseSoftwareDepthBuffer) {
Brian Paul5c3bee51999-12-10 19:09:21 +00001766 gl_alloc_depth_buffer( ctx );
Brian Paulfbd8f211999-11-11 01:22:25 +00001767 }
Brian Paul5c3bee51999-12-10 19:09:21 +00001768 if (ctx->DrawBuffer->UseSoftwareStencilBuffer) {
Brian Paulfbd8f211999-11-11 01:22:25 +00001769 gl_alloc_stencil_buffer( ctx );
1770 }
Brian Paul5c3bee51999-12-10 19:09:21 +00001771 if (ctx->DrawBuffer->UseSoftwareAccumBuffer) {
Brian Paulfbd8f211999-11-11 01:22:25 +00001772 gl_alloc_accum_buffer( ctx );
1773 }
1774 if (ctx->Visual->SoftwareAlpha) {
1775 gl_alloc_alpha_buffers( ctx );
1776 }
1777}
1778
jtgafb833d1999-08-19 00:55:39 +00001779
1780
1781/**********************************************************************/
1782/***** Miscellaneous functions *****/
1783/**********************************************************************/
1784
1785
1786/*
1787 * This function is called when the Mesa user has stumbled into a code
1788 * path which may not be implemented fully or correctly.
1789 */
1790void gl_problem( const GLcontext *ctx, const char *s )
1791{
1792 fprintf( stderr, "Mesa implementation error: %s\n", s );
1793 fprintf( stderr, "Report to mesa-bugs@mesa3d.org\n" );
1794 (void) ctx;
1795}
1796
1797
1798
1799/*
1800 * This is called to inform the user that he or she has tried to do
1801 * something illogical or if there's likely a bug in their program
1802 * (like enabled depth testing without a depth buffer).
1803 */
1804void gl_warning( const GLcontext *ctx, const char *s )
1805{
1806 GLboolean debug;
1807#ifdef DEBUG
1808 debug = GL_TRUE;
1809#else
1810 if (getenv("MESA_DEBUG")) {
1811 debug = GL_TRUE;
1812 }
1813 else {
1814 debug = GL_FALSE;
1815 }
1816#endif
1817 if (debug) {
1818 fprintf( stderr, "Mesa warning: %s\n", s );
1819 }
1820 (void) ctx;
1821}
1822
1823
1824
1825void gl_compile_error( GLcontext *ctx, GLenum error, const char *s )
1826{
1827 if (ctx->CompileFlag)
1828 gl_save_error( ctx, error, s );
1829
1830 if (ctx->ExecuteFlag)
1831 gl_error( ctx, error, s );
1832}
1833
1834
1835/*
1836 * This is Mesa's error handler. Normally, all that's done is the updating
1837 * of the current error value. If Mesa is compiled with -DDEBUG or if the
1838 * environment variable "MESA_DEBUG" is defined then a real error message
1839 * is printed to stderr.
1840 * Input: error - the error value
1841 * s - a diagnostic string
1842 */
1843void gl_error( GLcontext *ctx, GLenum error, const char *s )
1844{
1845 GLboolean debug;
1846
1847#ifdef DEBUG
1848 debug = GL_TRUE;
1849#else
1850 if (getenv("MESA_DEBUG")) {
1851 debug = GL_TRUE;
1852 }
1853 else {
1854 debug = GL_FALSE;
1855 }
1856#endif
1857
1858 if (debug) {
1859 char errstr[1000];
1860
1861 switch (error) {
1862 case GL_NO_ERROR:
1863 strcpy( errstr, "GL_NO_ERROR" );
1864 break;
1865 case GL_INVALID_VALUE:
1866 strcpy( errstr, "GL_INVALID_VALUE" );
1867 break;
1868 case GL_INVALID_ENUM:
1869 strcpy( errstr, "GL_INVALID_ENUM" );
1870 break;
1871 case GL_INVALID_OPERATION:
1872 strcpy( errstr, "GL_INVALID_OPERATION" );
1873 break;
1874 case GL_STACK_OVERFLOW:
1875 strcpy( errstr, "GL_STACK_OVERFLOW" );
1876 break;
1877 case GL_STACK_UNDERFLOW:
1878 strcpy( errstr, "GL_STACK_UNDERFLOW" );
1879 break;
1880 case GL_OUT_OF_MEMORY:
1881 strcpy( errstr, "GL_OUT_OF_MEMORY" );
1882 break;
1883 default:
1884 strcpy( errstr, "unknown" );
1885 break;
1886 }
1887 fprintf( stderr, "Mesa user error: %s in %s\n", errstr, s );
1888 }
1889
1890 if (ctx->ErrorValue==GL_NO_ERROR) {
1891 ctx->ErrorValue = error;
1892 }
1893
1894 /* Call device driver's error handler, if any. This is used on the Mac. */
1895 if (ctx->Driver.Error) {
1896 (*ctx->Driver.Error)( ctx );
1897 }
1898}
1899
1900
1901
jtgafb833d1999-08-19 00:55:39 +00001902/**********************************************************************/
1903/***** State update logic *****/
1904/**********************************************************************/
1905
1906
1907/*
1908 * Since the device driver may or may not support pixel logic ops we
1909 * have to make some extensive tests to determine whether or not
1910 * software-implemented logic operations have to be used.
1911 */
1912static void update_pixel_logic( GLcontext *ctx )
1913{
1914 if (ctx->Visual->RGBAflag) {
1915 /* RGBA mode blending w/ Logic Op */
1916 if (ctx->Color.ColorLogicOpEnabled) {
1917 if (ctx->Driver.LogicOp
1918 && (*ctx->Driver.LogicOp)( ctx, ctx->Color.LogicOp )) {
1919 /* Device driver can do logic, don't have to do it in software */
1920 ctx->Color.SWLogicOpEnabled = GL_FALSE;
1921 }
1922 else {
1923 /* Device driver can't do logic op so we do it in software */
1924 ctx->Color.SWLogicOpEnabled = GL_TRUE;
1925 }
1926 }
1927 else {
1928 /* no logic op */
1929 if (ctx->Driver.LogicOp) {
1930 (void) (*ctx->Driver.LogicOp)( ctx, GL_COPY );
1931 }
1932 ctx->Color.SWLogicOpEnabled = GL_FALSE;
1933 }
1934 }
1935 else {
1936 /* CI mode Logic Op */
1937 if (ctx->Color.IndexLogicOpEnabled) {
1938 if (ctx->Driver.LogicOp
1939 && (*ctx->Driver.LogicOp)( ctx, ctx->Color.LogicOp )) {
1940 /* Device driver can do logic, don't have to do it in software */
1941 ctx->Color.SWLogicOpEnabled = GL_FALSE;
1942 }
1943 else {
1944 /* Device driver can't do logic op so we do it in software */
1945 ctx->Color.SWLogicOpEnabled = GL_TRUE;
1946 }
1947 }
1948 else {
1949 /* no logic op */
1950 if (ctx->Driver.LogicOp) {
1951 (void) (*ctx->Driver.LogicOp)( ctx, GL_COPY );
1952 }
1953 ctx->Color.SWLogicOpEnabled = GL_FALSE;
1954 }
1955 }
1956}
1957
1958
1959
1960/*
1961 * Check if software implemented RGBA or Color Index masking is needed.
1962 */
1963static void update_pixel_masking( GLcontext *ctx )
1964{
1965 if (ctx->Visual->RGBAflag) {
1966 GLuint *colorMask = (GLuint *) ctx->Color.ColorMask;
1967 if (*colorMask == 0xffffffff) {
1968 /* disable masking */
1969 if (ctx->Driver.ColorMask) {
1970 (void) (*ctx->Driver.ColorMask)( ctx, GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE );
1971 }
1972 ctx->Color.SWmasking = GL_FALSE;
1973 }
1974 else {
1975 /* Ask driver to do color masking, if it can't then
1976 * do it in software
1977 */
1978 GLboolean red = ctx->Color.ColorMask[RCOMP] ? GL_TRUE : GL_FALSE;
1979 GLboolean green = ctx->Color.ColorMask[GCOMP] ? GL_TRUE : GL_FALSE;
1980 GLboolean blue = ctx->Color.ColorMask[BCOMP] ? GL_TRUE : GL_FALSE;
1981 GLboolean alpha = ctx->Color.ColorMask[ACOMP] ? GL_TRUE : GL_FALSE;
1982 if (ctx->Driver.ColorMask
1983 && (*ctx->Driver.ColorMask)( ctx, red, green, blue, alpha )) {
1984 ctx->Color.SWmasking = GL_FALSE;
1985 }
1986 else {
1987 ctx->Color.SWmasking = GL_TRUE;
1988 }
1989 }
1990 }
1991 else {
1992 if (ctx->Color.IndexMask==0xffffffff) {
1993 /* disable masking */
1994 if (ctx->Driver.IndexMask) {
1995 (void) (*ctx->Driver.IndexMask)( ctx, 0xffffffff );
1996 }
1997 ctx->Color.SWmasking = GL_FALSE;
1998 }
1999 else {
2000 /* Ask driver to do index masking, if it can't then
2001 * do it in software
2002 */
2003 if (ctx->Driver.IndexMask
2004 && (*ctx->Driver.IndexMask)( ctx, ctx->Color.IndexMask )) {
2005 ctx->Color.SWmasking = GL_FALSE;
2006 }
2007 else {
2008 ctx->Color.SWmasking = GL_TRUE;
2009 }
2010 }
2011 }
2012}
2013
2014
2015static void update_fog_mode( GLcontext *ctx )
2016{
Keith Whitwell2be79c11999-08-26 14:50:49 +00002017 int old_mode = ctx->FogMode;
2018
jtgafb833d1999-08-19 00:55:39 +00002019 if (ctx->Fog.Enabled) {
2020 if (ctx->Texture.Enabled)
2021 ctx->FogMode = FOG_FRAGMENT;
2022 else if (ctx->Hint.Fog == GL_NICEST)
2023 ctx->FogMode = FOG_FRAGMENT;
2024 else
2025 ctx->FogMode = FOG_VERTEX;
2026
2027 if (ctx->Driver.GetParameteri)
2028 if ((ctx->Driver.GetParameteri)( ctx, DD_HAVE_HARDWARE_FOG ))
2029 ctx->FogMode = FOG_FRAGMENT;
2030 }
2031 else {
2032 ctx->FogMode = FOG_NONE;
2033 }
Keith Whitwell2be79c11999-08-26 14:50:49 +00002034
2035 if (old_mode != ctx->FogMode)
2036 ctx->NewState |= NEW_FOG;
jtgafb833d1999-08-19 00:55:39 +00002037}
2038
2039
2040/*
2041 * Recompute the value of ctx->RasterMask, etc. according to
2042 * the current context.
2043 */
2044static void update_rasterflags( GLcontext *ctx )
2045{
2046 ctx->RasterMask = 0;
2047
2048 if (ctx->Color.AlphaEnabled) ctx->RasterMask |= ALPHATEST_BIT;
2049 if (ctx->Color.BlendEnabled) ctx->RasterMask |= BLEND_BIT;
2050 if (ctx->Depth.Test) ctx->RasterMask |= DEPTH_BIT;
2051 if (ctx->FogMode==FOG_FRAGMENT) ctx->RasterMask |= FOG_BIT;
2052 if (ctx->Color.SWLogicOpEnabled) ctx->RasterMask |= LOGIC_OP_BIT;
2053 if (ctx->Scissor.Enabled) ctx->RasterMask |= SCISSOR_BIT;
2054 if (ctx->Stencil.Enabled) ctx->RasterMask |= STENCIL_BIT;
2055 if (ctx->Color.SWmasking) ctx->RasterMask |= MASKING_BIT;
2056
2057 if (ctx->Visual->SoftwareAlpha && ctx->Color.ColorMask[ACOMP]
2058 && ctx->Color.DrawBuffer != GL_NONE)
2059 ctx->RasterMask |= ALPHABUF_BIT;
2060
2061 if ( ctx->Viewport.X<0
Brian Paul3f02f901999-11-24 18:48:30 +00002062 || ctx->Viewport.X + ctx->Viewport.Width > ctx->DrawBuffer->Width
jtgafb833d1999-08-19 00:55:39 +00002063 || ctx->Viewport.Y<0
Brian Paul3f02f901999-11-24 18:48:30 +00002064 || ctx->Viewport.Y + ctx->Viewport.Height > ctx->DrawBuffer->Height) {
jtgafb833d1999-08-19 00:55:39 +00002065 ctx->RasterMask |= WINCLIP_BIT;
2066 }
2067
2068 /* If we're not drawing to exactly one color buffer set the
2069 * MULTI_DRAW_BIT flag. Also set it if we're drawing to no
2070 * buffers or the RGBA or CI mask disables all writes.
2071 */
2072
2073 ctx->TriangleCaps &= ~DD_MULTIDRAW;
2074
2075 if (ctx->Color.MultiDrawBuffer) {
2076 ctx->RasterMask |= MULTI_DRAW_BIT;
2077 ctx->TriangleCaps |= DD_MULTIDRAW;
2078 }
2079 else if (ctx->Color.DrawBuffer==GL_NONE) {
2080 ctx->RasterMask |= MULTI_DRAW_BIT;
2081 ctx->TriangleCaps |= DD_MULTIDRAW;
2082 }
2083 else if (ctx->Visual->RGBAflag && ctx->Color.ColorMask==0) {
2084 /* all RGBA channels disabled */
2085 ctx->RasterMask |= MULTI_DRAW_BIT;
2086 ctx->TriangleCaps |= DD_MULTIDRAW;
2087 ctx->Color.DrawDestMask = 0;
2088 }
2089 else if (!ctx->Visual->RGBAflag && ctx->Color.IndexMask==0) {
2090 /* all color index bits disabled */
2091 ctx->RasterMask |= MULTI_DRAW_BIT;
2092 ctx->TriangleCaps |= DD_MULTIDRAW;
2093 ctx->Color.DrawDestMask = 0;
2094 }
2095}
2096
2097
2098void gl_print_state( const char *msg, GLuint state )
2099{
2100 fprintf(stderr,
2101 "%s: (0x%x) %s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s\n",
2102 msg,
2103 state,
2104 (state & NEW_LIGHTING) ? "lighting, " : "",
2105 (state & NEW_RASTER_OPS) ? "raster-ops, " : "",
2106 (state & NEW_TEXTURING) ? "texturing, " : "",
2107 (state & NEW_POLYGON) ? "polygon, " : "",
2108 (state & NEW_DRVSTATE0) ? "driver-0, " : "",
2109 (state & NEW_DRVSTATE1) ? "driver-1, " : "",
2110 (state & NEW_DRVSTATE2) ? "driver-2, " : "",
2111 (state & NEW_DRVSTATE3) ? "driver-3, " : "",
2112 (state & NEW_MODELVIEW) ? "modelview, " : "",
2113 (state & NEW_PROJECTION) ? "projection, " : "",
2114 (state & NEW_TEXTURE_MATRIX) ? "texture-matrix, " : "",
2115 (state & NEW_USER_CLIP) ? "user-clip, " : "",
2116 (state & NEW_TEXTURE_ENV) ? "texture-env, " : "",
2117 (state & NEW_CLIENT_STATE) ? "client-state, " : "",
2118 (state & NEW_FOG) ? "fog, " : "",
2119 (state & NEW_NORMAL_TRANSFORM) ? "normal-transform, " : "",
2120 (state & NEW_VIEWPORT) ? "viewport, " : "",
2121 (state & NEW_TEXTURE_ENABLE) ? "texture-enable, " : "");
2122}
2123
2124void gl_print_enable_flags( const char *msg, GLuint flags )
2125{
2126 fprintf(stderr,
2127 "%s: (0x%x) %s%s%s%s%s%s%s%s%s%s%s\n",
2128 msg,
2129 flags,
2130 (flags & ENABLE_TEX0) ? "tex-0, " : "",
2131 (flags & ENABLE_TEX1) ? "tex-1, " : "",
2132 (flags & ENABLE_LIGHT) ? "light, " : "",
2133 (flags & ENABLE_FOG) ? "fog, " : "",
2134 (flags & ENABLE_USERCLIP) ? "userclip, " : "",
2135 (flags & ENABLE_TEXGEN0) ? "tex-gen-0, " : "",
2136 (flags & ENABLE_TEXGEN1) ? "tex-gen-1, " : "",
2137 (flags & ENABLE_TEXMAT0) ? "tex-mat-0, " : "",
2138 (flags & ENABLE_TEXMAT1) ? "tex-mat-1, " : "",
2139 (flags & ENABLE_NORMALIZE) ? "normalize, " : "",
2140 (flags & ENABLE_RESCALE) ? "rescale, " : "");
2141}
2142
2143
2144/*
2145 * If ctx->NewState is non-zero then this function MUST be called before
2146 * rendering any primitive. Basically, function pointers and miscellaneous
2147 * flags are updated to reflect the current state of the state machine.
2148 */
2149void gl_update_state( GLcontext *ctx )
2150{
2151 GLuint i;
2152
2153 if (MESA_VERBOSE & VERBOSE_STATE)
2154 gl_print_state("", ctx->NewState);
2155
2156 if (ctx->NewState & NEW_CLIENT_STATE)
2157 gl_update_client_state( ctx );
2158
2159 if ((ctx->NewState & NEW_TEXTURE_ENABLE) &&
2160 (ctx->Enabled & ENABLE_TEX_ANY) != ctx->Texture.Enabled)
2161 ctx->NewState |= NEW_TEXTURING | NEW_RASTER_OPS;
2162
2163 if (ctx->NewState & NEW_TEXTURE_ENV) {
2164 if (ctx->Texture.Unit[0].EnvMode == ctx->Texture.Unit[0].LastEnvMode &&
2165 ctx->Texture.Unit[1].EnvMode == ctx->Texture.Unit[1].LastEnvMode)
2166 ctx->NewState &= ~NEW_TEXTURE_ENV;
2167 ctx->Texture.Unit[0].LastEnvMode = ctx->Texture.Unit[0].EnvMode;
2168 ctx->Texture.Unit[1].LastEnvMode = ctx->Texture.Unit[1].EnvMode;
2169 }
2170
jtgafb833d1999-08-19 00:55:39 +00002171 if (ctx->NewState & NEW_TEXTURE_MATRIX) {
2172 ctx->Enabled &= ~(ENABLE_TEXMAT0|ENABLE_TEXMAT1);
2173
2174 for (i=0; i < MAX_TEXTURE_UNITS; i++) {
2175 if (ctx->TextureMatrix[i].flags & MAT_DIRTY_ALL_OVER)
2176 {
2177 gl_matrix_analyze( &ctx->TextureMatrix[i] );
2178 ctx->TextureMatrix[i].flags &= ~MAT_DIRTY_DEPENDENTS;
2179
2180 if (ctx->Texture.Unit[i].Enabled &&
2181 ctx->TextureMatrix[i].type != MATRIX_IDENTITY)
2182 ctx->Enabled |= ENABLE_TEXMAT0 << i;
2183 }
2184 }
2185 }
2186
Brian Paulece75ac1999-11-15 22:21:47 +00002187 if (ctx->NewState & (NEW_TEXTURING | NEW_TEXTURE_ENABLE)) {
jtgafb833d1999-08-19 00:55:39 +00002188 ctx->Texture.NeedNormals = GL_FALSE;
2189 gl_update_dirty_texobjs(ctx);
2190 ctx->Enabled &= ~(ENABLE_TEXGEN0|ENABLE_TEXGEN1);
2191 ctx->Texture.ReallyEnabled = 0;
2192
2193 for (i=0; i < MAX_TEXTURE_UNITS; i++) {
2194 if (ctx->Texture.Unit[i].Enabled) {
2195 gl_update_texture_unit( ctx, &ctx->Texture.Unit[i] );
2196
2197 ctx->Texture.ReallyEnabled |=
2198 ctx->Texture.Unit[i].ReallyEnabled<<(i*4);
2199
2200 if (ctx->Texture.Unit[i].GenFlags != 0) {
2201 ctx->Enabled |= ENABLE_TEXGEN0 << i;
2202
2203 if (ctx->Texture.Unit[i].GenFlags & TEXGEN_NEED_NORMALS)
2204 {
2205 ctx->Texture.NeedNormals = GL_TRUE;
2206 ctx->Texture.NeedEyeCoords = GL_TRUE;
2207 }
2208
2209 if (ctx->Texture.Unit[i].GenFlags & TEXGEN_NEED_EYE_COORD)
2210 {
2211 ctx->Texture.NeedEyeCoords = GL_TRUE;
2212 }
2213 }
2214 }
2215 }
2216
2217 ctx->Texture.Enabled = ctx->Enabled & ENABLE_TEX_ANY;
2218 ctx->NeedNormals = (ctx->Light.Enabled || ctx->Texture.NeedNormals);
2219 }
2220
Keith Whitwell2be79c11999-08-26 14:50:49 +00002221 if (ctx->NewState & (NEW_RASTER_OPS | NEW_LIGHTING | NEW_FOG)) {
2222
2223
jtgafb833d1999-08-19 00:55:39 +00002224 if (ctx->NewState & NEW_RASTER_OPS) {
2225 update_pixel_logic(ctx);
2226 update_pixel_masking(ctx);
2227 update_fog_mode(ctx);
2228 update_rasterflags(ctx);
2229 if (ctx->Driver.Dither) {
2230 (*ctx->Driver.Dither)( ctx, ctx->Color.DitherFlag );
2231 }
2232
2233 /* Check if incoming colors can be modified during rasterization */
2234 if (ctx->Fog.Enabled ||
2235 ctx->Texture.Enabled ||
2236 ctx->Color.BlendEnabled ||
2237 ctx->Color.SWmasking ||
2238 ctx->Color.SWLogicOpEnabled) {
2239 ctx->MutablePixels = GL_TRUE;
2240 }
2241 else {
2242 ctx->MutablePixels = GL_FALSE;
2243 }
2244
2245 /* update scissor region */
2246
Brian Paul3f02f901999-11-24 18:48:30 +00002247 ctx->DrawBuffer->Xmin = 0;
2248 ctx->DrawBuffer->Ymin = 0;
2249 ctx->DrawBuffer->Xmax = ctx->DrawBuffer->Width-1;
2250 ctx->DrawBuffer->Ymax = ctx->DrawBuffer->Height-1;
jtgafb833d1999-08-19 00:55:39 +00002251 if (ctx->Scissor.Enabled) {
Brian Paul3f02f901999-11-24 18:48:30 +00002252 if (ctx->Scissor.X > ctx->DrawBuffer->Xmin) {
2253 ctx->DrawBuffer->Xmin = ctx->Scissor.X;
jtgafb833d1999-08-19 00:55:39 +00002254 }
Brian Paul3f02f901999-11-24 18:48:30 +00002255 if (ctx->Scissor.Y > ctx->DrawBuffer->Ymin) {
2256 ctx->DrawBuffer->Ymin = ctx->Scissor.Y;
jtgafb833d1999-08-19 00:55:39 +00002257 }
Brian Paul3f02f901999-11-24 18:48:30 +00002258 if (ctx->Scissor.X + ctx->Scissor.Width - 1 < ctx->DrawBuffer->Xmax) {
2259 ctx->DrawBuffer->Xmax = ctx->Scissor.X + ctx->Scissor.Width - 1;
jtgafb833d1999-08-19 00:55:39 +00002260 }
Brian Paul3f02f901999-11-24 18:48:30 +00002261 if (ctx->Scissor.Y + ctx->Scissor.Height - 1 < ctx->DrawBuffer->Ymax) {
2262 ctx->DrawBuffer->Ymax = ctx->Scissor.Y + ctx->Scissor.Height - 1;
jtgafb833d1999-08-19 00:55:39 +00002263 }
2264 }
jtgafb833d1999-08-19 00:55:39 +00002265 }
2266
2267 if (ctx->NewState & NEW_LIGHTING) {
Keith Whitwell2be79c11999-08-26 14:50:49 +00002268 ctx->TriangleCaps &= ~(DD_TRI_LIGHT_TWOSIDE|DD_LIGHTING_CULL);
jtgafb833d1999-08-19 00:55:39 +00002269 if (ctx->Light.Enabled) {
2270 if (ctx->Light.Model.TwoSide)
Keith Whitwell2be79c11999-08-26 14:50:49 +00002271 ctx->TriangleCaps |= (DD_TRI_LIGHT_TWOSIDE|DD_LIGHTING_CULL);
jtgafb833d1999-08-19 00:55:39 +00002272 gl_update_lighting(ctx);
2273 }
2274 }
2275 }
2276
2277 if (ctx->NewState & (NEW_POLYGON | NEW_LIGHTING)) {
2278
Keith Whitwellb6e69371999-09-02 13:16:17 +00002279 ctx->TriangleCaps &= ~DD_TRI_CULL_FRONT_BACK;
jtgafb833d1999-08-19 00:55:39 +00002280
2281 if (ctx->NewState & NEW_POLYGON) {
2282 /* Setup CullBits bitmask */
2283 if (ctx->Polygon.CullFlag) {
Keith Whitwell2be79c11999-08-26 14:50:49 +00002284 ctx->backface_sign = 1;
jtgafb833d1999-08-19 00:55:39 +00002285 switch(ctx->Polygon.CullFaceMode) {
jtgafb833d1999-08-19 00:55:39 +00002286 case GL_BACK:
Keith Whitwell2be79c11999-08-26 14:50:49 +00002287 if(ctx->Polygon.FrontFace==GL_CCW)
2288 ctx->backface_sign = -1;
jtgafb833d1999-08-19 00:55:39 +00002289 ctx->Polygon.CullBits = 1;
2290 break;
Keith Whitwell2be79c11999-08-26 14:50:49 +00002291 case GL_FRONT:
2292 if(ctx->Polygon.FrontFace!=GL_CCW)
2293 ctx->backface_sign = -1;
2294 ctx->Polygon.CullBits = 2;
2295 break;
jtgafb833d1999-08-19 00:55:39 +00002296 default:
2297 case GL_FRONT_AND_BACK:
Keith Whitwell2be79c11999-08-26 14:50:49 +00002298 ctx->backface_sign = 0;
Keith Whitwellb6e69371999-09-02 13:16:17 +00002299 ctx->Polygon.CullBits = 0;
2300 ctx->TriangleCaps |= DD_TRI_CULL_FRONT_BACK;
jtgafb833d1999-08-19 00:55:39 +00002301 break;
2302 }
2303 }
Keith Whitwell2be79c11999-08-26 14:50:49 +00002304 else {
jtgafb833d1999-08-19 00:55:39 +00002305 ctx->Polygon.CullBits = 3;
Keith Whitwell2be79c11999-08-26 14:50:49 +00002306 ctx->backface_sign = 0;
2307 }
jtgafb833d1999-08-19 00:55:39 +00002308
2309 /* Any Polygon offsets enabled? */
2310 ctx->TriangleCaps &= ~DD_TRI_OFFSET;
2311
2312 if (ctx->Polygon.OffsetPoint ||
2313 ctx->Polygon.OffsetLine ||
2314 ctx->Polygon.OffsetFill)
2315 ctx->TriangleCaps |= DD_TRI_OFFSET;
2316
2317 /* reset Z offsets now */
2318 ctx->PointZoffset = 0.0;
2319 ctx->LineZoffset = 0.0;
2320 ctx->PolygonZoffset = 0.0;
2321 }
2322 }
2323
Brian Paulece75ac1999-11-15 22:21:47 +00002324 if (ctx->NewState & ~(NEW_CLIENT_STATE|
jtgafb833d1999-08-19 00:55:39 +00002325 NEW_DRIVER_STATE|NEW_USER_CLIP|
2326 NEW_POLYGON))
2327 gl_update_clipmask(ctx);
2328
2329 if (ctx->NewState & (NEW_LIGHTING|
2330 NEW_RASTER_OPS|
2331 NEW_TEXTURING|
Brian Paulece75ac1999-11-15 22:21:47 +00002332 NEW_TEXTURE_ENABLE|
jtgafb833d1999-08-19 00:55:39 +00002333 NEW_TEXTURE_ENV|
2334 NEW_POLYGON|
2335 NEW_DRVSTATE0|
2336 NEW_DRVSTATE1|
2337 NEW_DRVSTATE2|
2338 NEW_DRVSTATE3|
2339 NEW_USER_CLIP))
2340 {
2341 ctx->IndirectTriangles = ctx->TriangleCaps & ~ctx->Driver.TriangleCaps;
2342 ctx->IndirectTriangles |= DD_SW_RASTERIZE;
2343
Keith Whitwell2be79c11999-08-26 14:50:49 +00002344 if (MESA_VERBOSE&VERBOSE_CULL)
2345 gl_print_tri_caps("initial indirect tris", ctx->IndirectTriangles);
2346
jtgafb833d1999-08-19 00:55:39 +00002347 ctx->Driver.PointsFunc = NULL;
2348 ctx->Driver.LineFunc = NULL;
2349 ctx->Driver.TriangleFunc = NULL;
2350 ctx->Driver.QuadFunc = NULL;
2351 ctx->Driver.RectFunc = NULL;
2352 ctx->Driver.RenderVBClippedTab = NULL;
2353 ctx->Driver.RenderVBCulledTab = NULL;
2354 ctx->Driver.RenderVBRawTab = NULL;
2355
2356 /*
2357 * Here the driver sets up all the ctx->Driver function pointers to
2358 * it's specific, private functions.
2359 */
2360 ctx->Driver.UpdateState(ctx);
2361
Keith Whitwell2be79c11999-08-26 14:50:49 +00002362 if (MESA_VERBOSE&VERBOSE_CULL)
2363 gl_print_tri_caps("indirect tris", ctx->IndirectTriangles);
2364
jtgafb833d1999-08-19 00:55:39 +00002365 /*
2366 * In case the driver didn't hook in an optimized point, line or
2367 * triangle function we'll now select "core/fallback" point, line
2368 * and triangle functions.
2369 */
2370 if (ctx->IndirectTriangles & DD_SW_RASTERIZE) {
2371 gl_set_point_function(ctx);
2372 gl_set_line_function(ctx);
2373 gl_set_triangle_function(ctx);
2374 gl_set_quad_function(ctx);
Keith Whitwell2be79c11999-08-26 14:50:49 +00002375
2376 if ((ctx->IndirectTriangles &
2377 (DD_TRI_SW_RASTERIZE|DD_QUAD_SW_RASTERIZE|DD_TRI_CULL)) ==
2378 (DD_TRI_SW_RASTERIZE|DD_QUAD_SW_RASTERIZE|DD_TRI_CULL))
2379 ctx->IndirectTriangles &= ~DD_TRI_CULL;
jtgafb833d1999-08-19 00:55:39 +00002380 }
2381
Keith Whitwell2be79c11999-08-26 14:50:49 +00002382 if (MESA_VERBOSE&VERBOSE_CULL)
2383 gl_print_tri_caps("indirect tris 2", ctx->IndirectTriangles);
2384
jtgafb833d1999-08-19 00:55:39 +00002385 gl_set_render_vb_function(ctx);
2386 }
2387
2388 /* Should only be calc'd when !need_eye_coords and not culling.
2389 */
2390 if (ctx->NewState & (NEW_MODELVIEW|NEW_PROJECTION)) {
2391 if (ctx->NewState & NEW_MODELVIEW) {
2392 gl_matrix_analyze( &ctx->ModelView );
2393 ctx->ProjectionMatrix.flags &= ~MAT_DIRTY_DEPENDENTS;
2394 }
2395
2396 if (ctx->NewState & NEW_PROJECTION) {
2397 gl_matrix_analyze( &ctx->ProjectionMatrix );
2398 ctx->ProjectionMatrix.flags &= ~MAT_DIRTY_DEPENDENTS;
2399
2400 if (ctx->Transform.AnyClip) {
2401 gl_update_userclip( ctx );
2402 }
2403 }
2404
2405 gl_calculate_model_project_matrix( ctx );
2406 ctx->ModelProjectWinMatrixUptodate = 0;
2407 }
2408
2409 /* Figure out whether we can light in object space or not. If we
2410 * can, find the current positions of the lights in object space
2411 */
Keith Whitwell2be79c11999-08-26 14:50:49 +00002412 if ((ctx->Enabled & (ENABLE_POINT_ATTEN | ENABLE_LIGHT | ENABLE_FOG |
jtgafb833d1999-08-19 00:55:39 +00002413 ENABLE_TEXGEN0 | ENABLE_TEXGEN1)) &&
2414 (ctx->NewState & (NEW_LIGHTING |
Keith Whitwell2be79c11999-08-26 14:50:49 +00002415 NEW_FOG |
jtgafb833d1999-08-19 00:55:39 +00002416 NEW_MODELVIEW |
2417 NEW_PROJECTION |
2418 NEW_TEXTURING |
2419 NEW_RASTER_OPS |
2420 NEW_USER_CLIP)))
2421 {
2422 GLboolean oldcoord, oldnorm;
2423
2424 oldcoord = ctx->NeedEyeCoords;
2425 oldnorm = ctx->NeedEyeNormals;
2426
2427 ctx->NeedNormals = (ctx->Light.Enabled || ctx->Texture.NeedNormals);
2428 ctx->NeedEyeCoords = ((ctx->Fog.Enabled && ctx->Hint.Fog != GL_NICEST) ||
2429 ctx->Point.Attenuated);
2430 ctx->NeedEyeNormals = GL_FALSE;
2431
2432 if (ctx->Light.Enabled) {
2433 if (ctx->Light.Flags & LIGHT_POSITIONAL) {
2434 /* Need length for attenuation */
2435 if (!TEST_MAT_FLAGS( &ctx->ModelView, MAT_FLAGS_LENGTH_PRESERVING))
2436 ctx->NeedEyeCoords = GL_TRUE;
2437 } else if (ctx->Light.NeedVertices) {
2438 /* Need angle for spot calculations */
2439 if (!TEST_MAT_FLAGS( &ctx->ModelView, MAT_FLAGS_ANGLE_PRESERVING))
2440 ctx->NeedEyeCoords = GL_TRUE;
2441 }
2442 ctx->NeedEyeNormals = ctx->NeedEyeCoords;
2443 }
2444 if (ctx->Texture.Enabled || ctx->RenderMode==GL_FEEDBACK) {
2445 if (ctx->Texture.NeedEyeCoords) ctx->NeedEyeCoords = GL_TRUE;
2446 if (ctx->Texture.NeedNormals)
2447 ctx->NeedNormals = ctx->NeedEyeNormals = GL_TRUE;
2448 }
2449
2450 ctx->vb_proj_matrix = &ctx->ModelProjectMatrix;
2451
2452 if (ctx->NeedEyeCoords)
2453 ctx->vb_proj_matrix = &ctx->ProjectionMatrix;
2454
2455 if (ctx->Light.Enabled) {
2456 gl_update_lighting_function(ctx);
2457
2458 if ( (ctx->NewState & NEW_LIGHTING) ||
2459 ((ctx->NewState & (NEW_MODELVIEW| NEW_PROJECTION)) &&
2460 !ctx->NeedEyeCoords) ||
2461 oldcoord != ctx->NeedEyeCoords ||
2462 oldnorm != ctx->NeedEyeNormals) {
2463 gl_compute_light_positions(ctx);
2464 }
2465
2466 ctx->rescale_factor = 1.0F;
2467
2468 if (ctx->ModelView.flags & (MAT_FLAG_UNIFORM_SCALE |
2469 MAT_FLAG_GENERAL_SCALE |
2470 MAT_FLAG_GENERAL_3D |
2471 MAT_FLAG_GENERAL) )
2472
2473 {
2474 GLfloat *m = ctx->ModelView.inv;
2475 GLfloat f = m[2]*m[2] + m[6]*m[6] + m[10]*m[10];
2476 if (f > 1e-12 && (f-1)*(f-1) > 1e-12)
2477 ctx->rescale_factor = 1.0/GL_SQRT(f);
2478 }
2479 }
2480
2481 gl_update_normal_transform( ctx );
2482 }
2483
jtgafb833d1999-08-19 00:55:39 +00002484 gl_update_pipelines(ctx);
2485 ctx->NewState = 0;
2486}