1287bdf2bf8e14d69640544fd56b36d264d68a58
[mesa.git] / src / mesa / main / texstate.c
1 /* $Id: texstate.c,v 1.79 2002/09/27 02:45:38 brianp 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 "colormac.h"
33 #include "context.h"
34 #include "enums.h"
35 #include "extensions.h"
36 #include "macros.h"
37 #include "texobj.h"
38 #include "teximage.h"
39 #include "texstate.h"
40 #include "mtypes.h"
41 #include "math/m_xform.h"
42 #include "math/m_matrix.h"
43 #endif
44
45
46
47 #ifdef SPECIALCAST
48 /* Needed for an Amiga compiler */
49 #define ENUM_TO_FLOAT(X) ((GLfloat)(GLint)(X))
50 #define ENUM_TO_DOUBLE(X) ((GLdouble)(GLint)(X))
51 #else
52 /* all other compilers */
53 #define ENUM_TO_FLOAT(X) ((GLfloat)(X))
54 #define ENUM_TO_DOUBLE(X) ((GLdouble)(X))
55 #endif
56
57
58
59 void
60 _mesa_copy_texture_state( const GLcontext *src, GLcontext *dst )
61 {
62 GLuint i;
63
64 ASSERT(src);
65 ASSERT(dst);
66
67 dst->Texture.CurrentUnit = src->Texture.CurrentUnit;
68 dst->Texture._GenFlags = src->Texture._GenFlags;
69 dst->Texture._TexGenEnabled = src->Texture._TexGenEnabled;
70 dst->Texture._TexMatEnabled = src->Texture._TexMatEnabled;
71 dst->Texture.SharedPalette = src->Texture.SharedPalette;
72
73 /* per-unit state */
74 for (i = 0; i < src->Const.MaxTextureUnits; i++) {
75 dst->Texture.Unit[i].Enabled = src->Texture.Unit[i].Enabled;
76 dst->Texture.Unit[i].EnvMode = src->Texture.Unit[i].EnvMode;
77 COPY_4V(dst->Texture.Unit[i].EnvColor, src->Texture.Unit[i].EnvColor);
78 dst->Texture.Unit[i].TexGenEnabled = src->Texture.Unit[i].TexGenEnabled;
79 dst->Texture.Unit[i].GenModeS = src->Texture.Unit[i].GenModeS;
80 dst->Texture.Unit[i].GenModeT = src->Texture.Unit[i].GenModeT;
81 dst->Texture.Unit[i].GenModeR = src->Texture.Unit[i].GenModeR;
82 dst->Texture.Unit[i].GenModeQ = src->Texture.Unit[i].GenModeQ;
83 dst->Texture.Unit[i]._GenBitS = src->Texture.Unit[i]._GenBitS;
84 dst->Texture.Unit[i]._GenBitT = src->Texture.Unit[i]._GenBitT;
85 dst->Texture.Unit[i]._GenBitR = src->Texture.Unit[i]._GenBitR;
86 dst->Texture.Unit[i]._GenBitQ = src->Texture.Unit[i]._GenBitQ;
87 dst->Texture.Unit[i]._GenFlags = src->Texture.Unit[i]._GenFlags;
88 COPY_4V(dst->Texture.Unit[i].ObjectPlaneS, src->Texture.Unit[i].ObjectPlaneS);
89 COPY_4V(dst->Texture.Unit[i].ObjectPlaneT, src->Texture.Unit[i].ObjectPlaneT);
90 COPY_4V(dst->Texture.Unit[i].ObjectPlaneR, src->Texture.Unit[i].ObjectPlaneR);
91 COPY_4V(dst->Texture.Unit[i].ObjectPlaneQ, src->Texture.Unit[i].ObjectPlaneQ);
92 COPY_4V(dst->Texture.Unit[i].EyePlaneS, src->Texture.Unit[i].EyePlaneS);
93 COPY_4V(dst->Texture.Unit[i].EyePlaneT, src->Texture.Unit[i].EyePlaneT);
94 COPY_4V(dst->Texture.Unit[i].EyePlaneR, src->Texture.Unit[i].EyePlaneR);
95 COPY_4V(dst->Texture.Unit[i].EyePlaneQ, src->Texture.Unit[i].EyePlaneQ);
96 dst->Texture.Unit[i].LodBias = src->Texture.Unit[i].LodBias;
97
98 /* GL_EXT_texture_env_combine */
99 dst->Texture.Unit[i].CombineModeRGB = src->Texture.Unit[i].CombineModeRGB;
100 dst->Texture.Unit[i].CombineModeA = src->Texture.Unit[i].CombineModeA;
101 COPY_3V(dst->Texture.Unit[i].CombineSourceRGB, src->Texture.Unit[i].CombineSourceRGB);
102 COPY_3V(dst->Texture.Unit[i].CombineSourceA, src->Texture.Unit[i].CombineSourceA);
103 COPY_3V(dst->Texture.Unit[i].CombineOperandRGB, src->Texture.Unit[i].CombineOperandRGB);
104 COPY_3V(dst->Texture.Unit[i].CombineOperandA, src->Texture.Unit[i].CombineOperandA);
105 dst->Texture.Unit[i].CombineScaleShiftRGB = src->Texture.Unit[i].CombineScaleShiftRGB;
106 dst->Texture.Unit[i].CombineScaleShiftA = src->Texture.Unit[i].CombineScaleShiftA;
107
108 /* texture object state */
109 _mesa_copy_texture_object(dst->Texture.Unit[i].Current1D,
110 src->Texture.Unit[i].Current1D);
111 _mesa_copy_texture_object(dst->Texture.Unit[i].Current2D,
112 src->Texture.Unit[i].Current2D);
113 _mesa_copy_texture_object(dst->Texture.Unit[i].Current3D,
114 src->Texture.Unit[i].Current3D);
115 _mesa_copy_texture_object(dst->Texture.Unit[i].CurrentCubeMap,
116 src->Texture.Unit[i].CurrentCubeMap);
117 }
118 }
119
120
121 /**********************************************************************/
122 /* Texture Environment */
123 /**********************************************************************/
124
125
126 void
127 _mesa_TexEnvfv( GLenum target, GLenum pname, const GLfloat *param )
128 {
129 GET_CURRENT_CONTEXT(ctx);
130 struct gl_texture_unit *texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
131 ASSERT_OUTSIDE_BEGIN_END(ctx);
132
133 #define TE_ERROR(errCode, msg, value) \
134 _mesa_error(ctx, errCode, msg, _mesa_lookup_enum_by_nr(value));
135
136 if (target == GL_TEXTURE_ENV) {
137 switch (pname) {
138 case GL_TEXTURE_ENV_MODE:
139 {
140 const GLenum mode = (GLenum) (GLint) *param;
141 if (mode == GL_MODULATE ||
142 mode == GL_BLEND ||
143 mode == GL_DECAL ||
144 mode == GL_REPLACE ||
145 (mode == GL_ADD && ctx->Extensions.EXT_texture_env_add) ||
146 (mode == GL_COMBINE_EXT &&
147 (ctx->Extensions.EXT_texture_env_combine ||
148 ctx->Extensions.ARB_texture_env_combine))) {
149 /* legal */
150 if (texUnit->EnvMode == mode)
151 return;
152 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
153 texUnit->EnvMode = mode;
154 }
155 else {
156 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(param=%s)", mode);
157 return;
158 }
159 }
160 break;
161 case GL_TEXTURE_ENV_COLOR:
162 {
163 GLfloat tmp[4];
164 tmp[0] = CLAMP( param[0], 0.0F, 1.0F );
165 tmp[1] = CLAMP( param[1], 0.0F, 1.0F );
166 tmp[2] = CLAMP( param[2], 0.0F, 1.0F );
167 tmp[3] = CLAMP( param[3], 0.0F, 1.0F );
168 if (TEST_EQ_4V(tmp, texUnit->EnvColor))
169 return;
170 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
171 COPY_4FV(texUnit->EnvColor, tmp);
172 }
173 break;
174 case GL_COMBINE_RGB_EXT:
175 if (ctx->Extensions.EXT_texture_env_combine ||
176 ctx->Extensions.ARB_texture_env_combine) {
177 const GLenum mode = (GLenum) (GLint) *param;
178 switch (mode) {
179 case GL_REPLACE:
180 case GL_MODULATE:
181 case GL_ADD:
182 case GL_ADD_SIGNED_EXT:
183 case GL_INTERPOLATE_EXT:
184 /* OK */
185 break;
186 case GL_SUBTRACT_ARB:
187 if (!ctx->Extensions.ARB_texture_env_combine) {
188 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(param=%s)", mode);
189 return;
190 }
191 break;
192 case GL_DOT3_RGB_EXT:
193 case GL_DOT3_RGBA_EXT:
194 if (!ctx->Extensions.EXT_texture_env_dot3) {
195 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(param=%s)", mode);
196 return;
197 }
198 break;
199 case GL_DOT3_RGB_ARB:
200 case GL_DOT3_RGBA_ARB:
201 if (!ctx->Extensions.ARB_texture_env_dot3) {
202 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(param=%s)", mode);
203 return;
204 }
205 break;
206 default:
207 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(param=%s)", mode);
208 return;
209 }
210 if (texUnit->CombineModeRGB == mode)
211 return;
212 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
213 texUnit->CombineModeRGB = mode;
214 }
215 else {
216 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(pname=%s)", pname);
217 return;
218 }
219 break;
220 case GL_COMBINE_ALPHA_EXT:
221 if (ctx->Extensions.EXT_texture_env_combine ||
222 ctx->Extensions.ARB_texture_env_combine) {
223 const GLenum mode = (GLenum) (GLint) *param;
224 if (mode == GL_REPLACE ||
225 mode == GL_MODULATE ||
226 mode == GL_ADD ||
227 mode == GL_ADD_SIGNED_EXT ||
228 mode == GL_INTERPOLATE_EXT ||
229 (mode == GL_SUBTRACT_ARB &&
230 ctx->Extensions.ARB_texture_env_combine)) {
231 /* legal */
232 if (texUnit->CombineModeA == mode)
233 return;
234 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
235 texUnit->CombineModeA = mode;
236 }
237 else {
238 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(param=%s)", mode);
239 return;
240 }
241 }
242 else {
243 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(pname=%s)", pname);
244 return;
245 }
246 break;
247 case GL_SOURCE0_RGB_EXT:
248 case GL_SOURCE1_RGB_EXT:
249 case GL_SOURCE2_RGB_EXT:
250 if (ctx->Extensions.EXT_texture_env_combine ||
251 ctx->Extensions.ARB_texture_env_combine) {
252 const GLenum source = (GLenum) (GLint) *param;
253 const GLuint s = pname - GL_SOURCE0_RGB_EXT;
254 if (source == GL_TEXTURE ||
255 source == GL_CONSTANT_EXT ||
256 source == GL_PRIMARY_COLOR_EXT ||
257 source == GL_PREVIOUS_EXT ||
258 (ctx->Extensions.ARB_texture_env_crossbar &&
259 source >= GL_TEXTURE0_ARB &&
260 source < GL_TEXTURE0_ARB + ctx->Const.MaxTextureUnits)) {
261 /* legal */
262 if (texUnit->CombineSourceRGB[s] == source)
263 return;
264 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
265 texUnit->CombineSourceRGB[s] = source;
266 }
267 else {
268 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(param=%s)", source);
269 return;
270 }
271 }
272 else {
273 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(pname=%s)", pname);
274 return;
275 }
276 break;
277 case GL_SOURCE0_ALPHA_EXT:
278 case GL_SOURCE1_ALPHA_EXT:
279 case GL_SOURCE2_ALPHA_EXT:
280 if (ctx->Extensions.EXT_texture_env_combine ||
281 ctx->Extensions.ARB_texture_env_combine) {
282 const GLenum source = (GLenum) (GLint) *param;
283 const GLuint s = pname - GL_SOURCE0_ALPHA_EXT;
284 if (source == GL_TEXTURE ||
285 source == GL_CONSTANT_EXT ||
286 source == GL_PRIMARY_COLOR_EXT ||
287 source == GL_PREVIOUS_EXT ||
288 (ctx->Extensions.ARB_texture_env_crossbar &&
289 source >= GL_TEXTURE0_ARB &&
290 source < GL_TEXTURE0_ARB + ctx->Const.MaxTextureUnits)) {
291 /* legal */
292 if (texUnit->CombineSourceA[s] == source)
293 return;
294 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
295 texUnit->CombineSourceA[s] = source;
296 }
297 else {
298 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(param=%s)", source);
299 return;
300 }
301 }
302 else {
303 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(pname=%s)", pname);
304 return;
305 }
306 break;
307 case GL_OPERAND0_RGB_EXT:
308 case GL_OPERAND1_RGB_EXT:
309 if (ctx->Extensions.EXT_texture_env_combine ||
310 ctx->Extensions.ARB_texture_env_combine) {
311 const GLenum operand = (GLenum) (GLint) *param;
312 const GLuint s = pname - GL_OPERAND0_RGB_EXT;
313 switch (operand) {
314 case GL_SRC_COLOR:
315 case GL_ONE_MINUS_SRC_COLOR:
316 case GL_SRC_ALPHA:
317 case GL_ONE_MINUS_SRC_ALPHA:
318 if (texUnit->CombineOperandRGB[s] == operand)
319 return;
320 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
321 texUnit->CombineOperandRGB[s] = operand;
322 break;
323 default:
324 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(param=%s)", operand);
325 return;
326 }
327 }
328 else {
329 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(pname=%s)", pname);
330 return;
331 }
332 break;
333 case GL_OPERAND0_ALPHA_EXT:
334 case GL_OPERAND1_ALPHA_EXT:
335 if (ctx->Extensions.EXT_texture_env_combine ||
336 ctx->Extensions.ARB_texture_env_combine) {
337 const GLenum operand = (GLenum) (GLint) *param;
338 switch (operand) {
339 case GL_SRC_ALPHA:
340 case GL_ONE_MINUS_SRC_ALPHA:
341 if (texUnit->CombineOperandA[pname-GL_OPERAND0_ALPHA_EXT] ==
342 operand)
343 return;
344 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
345 texUnit->CombineOperandA[pname-GL_OPERAND0_ALPHA_EXT] = operand;
346 break;
347 default:
348 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(param=%s)", operand);
349 return;
350 }
351 }
352 else {
353 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(pname=%s)", pname);
354 return;
355 }
356 break;
357 case GL_OPERAND2_RGB_EXT:
358 if (ctx->Extensions.EXT_texture_env_combine ||
359 ctx->Extensions.ARB_texture_env_combine) {
360 const GLenum operand = (GLenum) (GLint) *param;
361 switch (operand) {
362 case GL_SRC_COLOR: /* ARB combine only */
363 case GL_ONE_MINUS_SRC_COLOR: /* ARB combine only */
364 case GL_SRC_ALPHA:
365 case GL_ONE_MINUS_SRC_ALPHA: /* ARB combine only */
366 if (texUnit->CombineOperandRGB[2] == operand)
367 return;
368 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
369 texUnit->CombineOperandRGB[2] = operand;
370 default:
371 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(param=%s)", operand);
372 return;
373 }
374 }
375 else {
376 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(pname=%s)", pname);
377 return;
378 }
379 break;
380 case GL_OPERAND2_ALPHA_EXT:
381 if (ctx->Extensions.EXT_texture_env_combine ||
382 ctx->Extensions.ARB_texture_env_combine) {
383 const GLenum operand = (GLenum) (GLint) *param;
384 switch (operand) {
385 case GL_SRC_ALPHA:
386 case GL_ONE_MINUS_SRC_ALPHA: /* ARB combine only */
387 if (texUnit->CombineOperandA[2] == operand)
388 return;
389 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
390 texUnit->CombineOperandA[2] = operand;
391 break;
392 default:
393 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(param=%s)", operand);
394 return;
395 }
396 }
397 else {
398 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(pname=%s)", pname);
399 return;
400 }
401 break;
402 case GL_RGB_SCALE_EXT:
403 if (ctx->Extensions.EXT_texture_env_combine ||
404 ctx->Extensions.ARB_texture_env_combine) {
405 GLuint newshift;
406 if (*param == 1.0) {
407 newshift = 0;
408 }
409 else if (*param == 2.0) {
410 newshift = 1;
411 }
412 else if (*param == 4.0) {
413 newshift = 2;
414 }
415 else {
416 _mesa_error( ctx, GL_INVALID_VALUE,
417 "glTexEnv(GL_RGB_SCALE not 1, 2 or 4)" );
418 return;
419 }
420 if (texUnit->CombineScaleShiftRGB == newshift)
421 return;
422 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
423 texUnit->CombineScaleShiftRGB = newshift;
424 }
425 else {
426 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(pname=%s)", pname);
427 return;
428 }
429 break;
430 case GL_ALPHA_SCALE:
431 if (ctx->Extensions.EXT_texture_env_combine ||
432 ctx->Extensions.ARB_texture_env_combine) {
433 GLuint newshift;
434 if (*param == 1.0) {
435 newshift = 0;
436 }
437 else if (*param == 2.0) {
438 newshift = 1;
439 }
440 else if (*param == 4.0) {
441 newshift = 2;
442 }
443 else {
444 _mesa_error( ctx, GL_INVALID_VALUE,
445 "glTexEnv(GL_ALPHA_SCALE not 1, 2 or 4)" );
446 return;
447 }
448 if (texUnit->CombineScaleShiftA == newshift)
449 return;
450 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
451 texUnit->CombineScaleShiftA = newshift;
452 }
453 else {
454 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(pname=%s)", pname);
455 return;
456 }
457 break;
458 default:
459 _mesa_error( ctx, GL_INVALID_ENUM, "glTexEnv(pname)" );
460 return;
461 }
462 }
463 else if (target == GL_TEXTURE_FILTER_CONTROL_EXT) {
464 /* GL_EXT_texture_lod_bias */
465 if (!ctx->Extensions.EXT_texture_lod_bias) {
466 _mesa_error( ctx, GL_INVALID_ENUM, "glTexEnv(target=0x%x)", target );
467 return;
468 }
469 if (pname == GL_TEXTURE_LOD_BIAS_EXT) {
470 if (texUnit->LodBias == param[0])
471 return;
472 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
473 texUnit->LodBias = CLAMP(param[0], -ctx->Const.MaxTextureLodBias,
474 ctx->Const.MaxTextureLodBias);
475 }
476 else {
477 TE_ERROR(GL_INVALID_ENUM, "glTexEnv(pname=%s)", pname);
478 return;
479 }
480 }
481 else if (target == GL_POINT_SPRITE_NV) {
482 /* GL_NV_point_sprite */
483 if (!ctx->Extensions.NV_point_sprite) {
484 _mesa_error( ctx, GL_INVALID_ENUM, "glTexEnv(target=0x%x)", target );
485 return;
486 }
487 if (pname == GL_COORD_REPLACE_NV) {
488 const GLenum value = (GLenum) param[0];
489 if (value == GL_TRUE || value == GL_FALSE) {
490 /* It's kind of weird to set point state via glTexEnv,
491 * but that's what the spec calls for.
492 */
493 const GLboolean state = (GLboolean) value;
494 if (ctx->Point.CoordReplace[ctx->Texture.CurrentUnit] == state)
495 return;
496 FLUSH_VERTICES(ctx, _NEW_POINT);
497 ctx->Point.CoordReplace[ctx->Texture.CurrentUnit] = state;
498 }
499 else {
500 _mesa_error( ctx, GL_INVALID_VALUE, "glTexEnv(param=0x%x)", value);
501 return;
502 }
503 }
504 else {
505 _mesa_error( ctx, GL_INVALID_ENUM, "glTexEnv(pname=0x%x)", pname );
506 return;
507 }
508 }
509 else {
510 _mesa_error( ctx, GL_INVALID_ENUM, "glTexEnv(target=0x%x)",target );
511 return;
512 }
513
514 if (MESA_VERBOSE&(VERBOSE_API|VERBOSE_TEXTURE))
515 _mesa_debug(ctx, "glTexEnv %s %s %.1f(%s) ...\n",
516 _mesa_lookup_enum_by_nr(target),
517 _mesa_lookup_enum_by_nr(pname),
518 *param,
519 _mesa_lookup_enum_by_nr((GLenum) (GLint) *param));
520
521 /* Tell device driver about the new texture environment */
522 if (ctx->Driver.TexEnv) {
523 (*ctx->Driver.TexEnv)( ctx, target, pname, param );
524 }
525 }
526
527
528 void
529 _mesa_TexEnvf( GLenum target, GLenum pname, GLfloat param )
530 {
531 _mesa_TexEnvfv( target, pname, &param );
532 }
533
534
535
536 void
537 _mesa_TexEnvi( GLenum target, GLenum pname, GLint param )
538 {
539 GLfloat p[4];
540 p[0] = (GLfloat) param;
541 p[1] = p[2] = p[3] = 0.0;
542 _mesa_TexEnvfv( target, pname, p );
543 }
544
545
546 void
547 _mesa_TexEnviv( GLenum target, GLenum pname, const GLint *param )
548 {
549 GLfloat p[4];
550 if (pname == GL_TEXTURE_ENV_COLOR) {
551 p[0] = INT_TO_FLOAT( param[0] );
552 p[1] = INT_TO_FLOAT( param[1] );
553 p[2] = INT_TO_FLOAT( param[2] );
554 p[3] = INT_TO_FLOAT( param[3] );
555 }
556 else {
557 p[0] = (GLint) param[0];
558 p[1] = p[2] = p[3] = 0; /* init to zero, just to be safe */
559 }
560 _mesa_TexEnvfv( target, pname, p );
561 }
562
563
564 void
565 _mesa_GetTexEnvfv( GLenum target, GLenum pname, GLfloat *params )
566 {
567 GET_CURRENT_CONTEXT(ctx);
568 const struct gl_texture_unit *texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
569 ASSERT_OUTSIDE_BEGIN_END(ctx);
570
571 if (target == GL_TEXTURE_ENV) {
572 switch (pname) {
573 case GL_TEXTURE_ENV_MODE:
574 *params = ENUM_TO_FLOAT(texUnit->EnvMode);
575 break;
576 case GL_TEXTURE_ENV_COLOR:
577 COPY_4FV( params, texUnit->EnvColor );
578 break;
579 case GL_COMBINE_RGB_EXT:
580 if (ctx->Extensions.EXT_texture_env_combine ||
581 ctx->Extensions.ARB_texture_env_combine) {
582 *params = (GLfloat) texUnit->CombineModeRGB;
583 }
584 else {
585 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
586 }
587 break;
588 case GL_COMBINE_ALPHA_EXT:
589 if (ctx->Extensions.EXT_texture_env_combine ||
590 ctx->Extensions.ARB_texture_env_combine) {
591 *params = (GLfloat) texUnit->CombineModeA;
592 }
593 else {
594 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
595 }
596 break;
597 case GL_SOURCE0_RGB_EXT:
598 if (ctx->Extensions.EXT_texture_env_combine ||
599 ctx->Extensions.ARB_texture_env_combine) {
600 *params = (GLfloat) texUnit->CombineSourceRGB[0];
601 }
602 else {
603 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
604 }
605 break;
606 case GL_SOURCE1_RGB_EXT:
607 if (ctx->Extensions.EXT_texture_env_combine ||
608 ctx->Extensions.ARB_texture_env_combine) {
609 *params = (GLfloat) texUnit->CombineSourceRGB[1];
610 }
611 else {
612 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
613 }
614 break;
615 case GL_SOURCE2_RGB_EXT:
616 if (ctx->Extensions.EXT_texture_env_combine ||
617 ctx->Extensions.ARB_texture_env_combine) {
618 *params = (GLfloat) texUnit->CombineSourceRGB[2];
619 }
620 else {
621 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
622 }
623 break;
624 case GL_SOURCE0_ALPHA_EXT:
625 if (ctx->Extensions.EXT_texture_env_combine ||
626 ctx->Extensions.ARB_texture_env_combine) {
627 *params = (GLfloat) texUnit->CombineSourceA[0];
628 }
629 else {
630 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
631 }
632 break;
633 case GL_SOURCE1_ALPHA_EXT:
634 if (ctx->Extensions.EXT_texture_env_combine ||
635 ctx->Extensions.ARB_texture_env_combine) {
636 *params = (GLfloat) texUnit->CombineSourceA[1];
637 }
638 else {
639 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
640 }
641 break;
642 case GL_SOURCE2_ALPHA_EXT:
643 if (ctx->Extensions.EXT_texture_env_combine ||
644 ctx->Extensions.ARB_texture_env_combine) {
645 *params = (GLfloat) texUnit->CombineSourceA[2];
646 }
647 else {
648 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
649 }
650 break;
651 case GL_OPERAND0_RGB_EXT:
652 if (ctx->Extensions.EXT_texture_env_combine ||
653 ctx->Extensions.ARB_texture_env_combine) {
654 *params = (GLfloat) texUnit->CombineOperandRGB[0];
655 }
656 else {
657 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
658 }
659 break;
660 case GL_OPERAND1_RGB_EXT:
661 if (ctx->Extensions.EXT_texture_env_combine ||
662 ctx->Extensions.ARB_texture_env_combine) {
663 *params = (GLfloat) texUnit->CombineOperandRGB[1];
664 }
665 else {
666 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
667 }
668 break;
669 case GL_OPERAND2_RGB_EXT:
670 if (ctx->Extensions.EXT_texture_env_combine ||
671 ctx->Extensions.ARB_texture_env_combine) {
672 *params = (GLfloat) texUnit->CombineOperandRGB[2];
673 }
674 else {
675 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
676 }
677 break;
678 case GL_OPERAND0_ALPHA_EXT:
679 if (ctx->Extensions.EXT_texture_env_combine ||
680 ctx->Extensions.ARB_texture_env_combine) {
681 *params = (GLfloat) texUnit->CombineOperandA[0];
682 }
683 else {
684 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
685 }
686 break;
687 case GL_OPERAND1_ALPHA_EXT:
688 if (ctx->Extensions.EXT_texture_env_combine ||
689 ctx->Extensions.ARB_texture_env_combine) {
690 *params = (GLfloat) texUnit->CombineOperandA[1];
691 }
692 else {
693 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
694 }
695 break;
696 case GL_OPERAND2_ALPHA_EXT:
697 if (ctx->Extensions.EXT_texture_env_combine ||
698 ctx->Extensions.ARB_texture_env_combine) {
699 *params = (GLfloat) texUnit->CombineOperandA[2];
700 }
701 else {
702 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
703 }
704 break;
705 case GL_RGB_SCALE_EXT:
706 if (ctx->Extensions.EXT_texture_env_combine ||
707 ctx->Extensions.ARB_texture_env_combine) {
708 if (texUnit->CombineScaleShiftRGB == 0)
709 *params = 1.0;
710 else if (texUnit->CombineScaleShiftRGB == 1)
711 *params = 2.0;
712 else
713 *params = 4.0;
714 }
715 else {
716 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
717 return;
718 }
719 break;
720 case GL_ALPHA_SCALE:
721 if (ctx->Extensions.EXT_texture_env_combine ||
722 ctx->Extensions.ARB_texture_env_combine) {
723 if (texUnit->CombineScaleShiftA == 0)
724 *params = 1.0;
725 else if (texUnit->CombineScaleShiftA == 1)
726 *params = 2.0;
727 else
728 *params = 4.0;
729 }
730 else {
731 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)");
732 return;
733 }
734 break;
735 default:
736 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)" );
737 }
738 }
739 else if (target == GL_TEXTURE_FILTER_CONTROL_EXT) {
740 /* GL_EXT_texture_lod_bias */
741 if (!ctx->Extensions.EXT_texture_lod_bias) {
742 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexEnvfv(target)" );
743 return;
744 }
745 if (pname == GL_TEXTURE_LOD_BIAS_EXT) {
746 *params = texUnit->LodBias;
747 }
748 else {
749 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)" );
750 return;
751 }
752 }
753 else if (target == GL_POINT_SPRITE_NV) {
754 /* GL_NV_point_sprite */
755 if (!ctx->Extensions.NV_point_sprite) {
756 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexEnvfv(target)" );
757 return;
758 }
759 if (pname == GL_COORD_REPLACE_NV) {
760 *params = (GLfloat) ctx->Point.CoordReplace[ctx->Texture.CurrentUnit];
761 }
762 else {
763 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexEnvfv(pname)" );
764 return;
765 }
766 }
767 else {
768 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexEnvfv(target)" );
769 return;
770 }
771 }
772
773
774 void
775 _mesa_GetTexEnviv( GLenum target, GLenum pname, GLint *params )
776 {
777 GET_CURRENT_CONTEXT(ctx);
778 const struct gl_texture_unit *texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
779 ASSERT_OUTSIDE_BEGIN_END(ctx);
780
781 if (target == GL_TEXTURE_ENV) {
782 switch (pname) {
783 case GL_TEXTURE_ENV_MODE:
784 *params = (GLint) texUnit->EnvMode;
785 break;
786 case GL_TEXTURE_ENV_COLOR:
787 params[0] = FLOAT_TO_INT( texUnit->EnvColor[0] );
788 params[1] = FLOAT_TO_INT( texUnit->EnvColor[1] );
789 params[2] = FLOAT_TO_INT( texUnit->EnvColor[2] );
790 params[3] = FLOAT_TO_INT( texUnit->EnvColor[3] );
791 break;
792 case GL_COMBINE_RGB_EXT:
793 if (ctx->Extensions.EXT_texture_env_combine ||
794 ctx->Extensions.ARB_texture_env_combine) {
795 *params = (GLint) texUnit->CombineModeRGB;
796 }
797 else {
798 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
799 }
800 break;
801 case GL_COMBINE_ALPHA_EXT:
802 if (ctx->Extensions.EXT_texture_env_combine ||
803 ctx->Extensions.ARB_texture_env_combine) {
804 *params = (GLint) texUnit->CombineModeA;
805 }
806 else {
807 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
808 }
809 break;
810 case GL_SOURCE0_RGB_EXT:
811 if (ctx->Extensions.EXT_texture_env_combine ||
812 ctx->Extensions.ARB_texture_env_combine) {
813 *params = (GLint) texUnit->CombineSourceRGB[0];
814 }
815 else {
816 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
817 }
818 break;
819 case GL_SOURCE1_RGB_EXT:
820 if (ctx->Extensions.EXT_texture_env_combine ||
821 ctx->Extensions.ARB_texture_env_combine) {
822 *params = (GLint) texUnit->CombineSourceRGB[1];
823 }
824 else {
825 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
826 }
827 break;
828 case GL_SOURCE2_RGB_EXT:
829 if (ctx->Extensions.EXT_texture_env_combine ||
830 ctx->Extensions.ARB_texture_env_combine) {
831 *params = (GLint) texUnit->CombineSourceRGB[2];
832 }
833 else {
834 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
835 }
836 break;
837 case GL_SOURCE0_ALPHA_EXT:
838 if (ctx->Extensions.EXT_texture_env_combine ||
839 ctx->Extensions.ARB_texture_env_combine) {
840 *params = (GLint) texUnit->CombineSourceA[0];
841 }
842 else {
843 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
844 }
845 break;
846 case GL_SOURCE1_ALPHA_EXT:
847 if (ctx->Extensions.EXT_texture_env_combine ||
848 ctx->Extensions.ARB_texture_env_combine) {
849 *params = (GLint) texUnit->CombineSourceA[1];
850 }
851 else {
852 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
853 }
854 break;
855 case GL_SOURCE2_ALPHA_EXT:
856 if (ctx->Extensions.EXT_texture_env_combine ||
857 ctx->Extensions.ARB_texture_env_combine) {
858 *params = (GLint) texUnit->CombineSourceA[2];
859 }
860 else {
861 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
862 }
863 break;
864 case GL_OPERAND0_RGB_EXT:
865 if (ctx->Extensions.EXT_texture_env_combine ||
866 ctx->Extensions.ARB_texture_env_combine) {
867 *params = (GLint) texUnit->CombineOperandRGB[0];
868 }
869 else {
870 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
871 }
872 break;
873 case GL_OPERAND1_RGB_EXT:
874 if (ctx->Extensions.EXT_texture_env_combine ||
875 ctx->Extensions.ARB_texture_env_combine) {
876 *params = (GLint) texUnit->CombineOperandRGB[1];
877 }
878 else {
879 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
880 }
881 break;
882 case GL_OPERAND2_RGB_EXT:
883 if (ctx->Extensions.EXT_texture_env_combine ||
884 ctx->Extensions.ARB_texture_env_combine) {
885 *params = (GLint) texUnit->CombineOperandRGB[2];
886 }
887 else {
888 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
889 }
890 break;
891 case GL_OPERAND0_ALPHA_EXT:
892 if (ctx->Extensions.EXT_texture_env_combine ||
893 ctx->Extensions.ARB_texture_env_combine) {
894 *params = (GLint) texUnit->CombineOperandA[0];
895 }
896 else {
897 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
898 }
899 break;
900 case GL_OPERAND1_ALPHA_EXT:
901 if (ctx->Extensions.EXT_texture_env_combine ||
902 ctx->Extensions.ARB_texture_env_combine) {
903 *params = (GLint) texUnit->CombineOperandA[1];
904 }
905 else {
906 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
907 }
908 break;
909 case GL_OPERAND2_ALPHA_EXT:
910 if (ctx->Extensions.EXT_texture_env_combine ||
911 ctx->Extensions.ARB_texture_env_combine) {
912 *params = (GLint) texUnit->CombineOperandA[2];
913 }
914 else {
915 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
916 }
917 break;
918 case GL_RGB_SCALE_EXT:
919 if (ctx->Extensions.EXT_texture_env_combine ||
920 ctx->Extensions.ARB_texture_env_combine) {
921 if (texUnit->CombineScaleShiftRGB == 0)
922 *params = 1;
923 else if (texUnit->CombineScaleShiftRGB == 1)
924 *params = 2;
925 else
926 *params = 4;
927 }
928 else {
929 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
930 return;
931 }
932 break;
933 case GL_ALPHA_SCALE:
934 if (ctx->Extensions.EXT_texture_env_combine ||
935 ctx->Extensions.ARB_texture_env_combine) {
936 if (texUnit->CombineScaleShiftA == 0)
937 *params = 1;
938 else if (texUnit->CombineScaleShiftA == 1)
939 *params = 2;
940 else
941 *params = 4;
942 }
943 else {
944 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)");
945 return;
946 }
947 break;
948 default:
949 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)" );
950 }
951 }
952 else if (target == GL_TEXTURE_FILTER_CONTROL_EXT) {
953 /* GL_EXT_texture_lod_bias */
954 if (!ctx->Extensions.EXT_texture_lod_bias) {
955 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexEnviv(target)" );
956 return;
957 }
958 if (pname == GL_TEXTURE_LOD_BIAS_EXT) {
959 *params = (GLint) texUnit->LodBias;
960 }
961 else {
962 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)" );
963 return;
964 }
965 }
966 else if (target == GL_POINT_SPRITE_NV) {
967 /* GL_NV_point_sprite */
968 if (!ctx->Extensions.NV_point_sprite) {
969 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexEnviv(target)" );
970 return;
971 }
972 if (pname == GL_COORD_REPLACE_NV) {
973 *params = (GLint) ctx->Point.CoordReplace[ctx->Texture.CurrentUnit];
974 }
975 else {
976 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexEnviv(pname)" );
977 return;
978 }
979 }
980 else {
981 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexEnviv(target)" );
982 return;
983 }
984 }
985
986
987
988
989 /**********************************************************************/
990 /* Texture Parameters */
991 /**********************************************************************/
992
993
994 void
995 _mesa_TexParameterf( GLenum target, GLenum pname, GLfloat param )
996 {
997 _mesa_TexParameterfv(target, pname, &param);
998 }
999
1000
1001 void
1002 _mesa_TexParameterfv( GLenum target, GLenum pname, const GLfloat *params )
1003 {
1004 GET_CURRENT_CONTEXT(ctx);
1005 struct gl_texture_unit *texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
1006 GLenum eparam = (GLenum) (GLint) params[0];
1007 struct gl_texture_object *texObj;
1008 ASSERT_OUTSIDE_BEGIN_END(ctx);
1009
1010 if (MESA_VERBOSE&(VERBOSE_API|VERBOSE_TEXTURE))
1011 _mesa_debug(ctx, "texPARAM %s %s %d...\n",
1012 _mesa_lookup_enum_by_nr(target),
1013 _mesa_lookup_enum_by_nr(pname),
1014 eparam);
1015
1016
1017 switch (target) {
1018 case GL_TEXTURE_1D:
1019 texObj = texUnit->Current1D;
1020 break;
1021 case GL_TEXTURE_2D:
1022 texObj = texUnit->Current2D;
1023 break;
1024 case GL_TEXTURE_3D_EXT:
1025 texObj = texUnit->Current3D;
1026 break;
1027 case GL_TEXTURE_CUBE_MAP_ARB:
1028 if (!ctx->Extensions.ARB_texture_cube_map) {
1029 _mesa_error( ctx, GL_INVALID_ENUM, "glTexParameter(target)" );
1030 return;
1031 }
1032 texObj = texUnit->CurrentCubeMap;
1033 break;
1034 case GL_TEXTURE_RECTANGLE_NV:
1035 if (!ctx->Extensions.NV_texture_rectangle) {
1036 _mesa_error( ctx, GL_INVALID_ENUM, "glTexParameter(target)" );
1037 return;
1038 }
1039 texObj = texUnit->CurrentRect;
1040 break;
1041 default:
1042 _mesa_error( ctx, GL_INVALID_ENUM, "glTexParameter(target)" );
1043 return;
1044 }
1045
1046 switch (pname) {
1047 case GL_TEXTURE_MIN_FILTER:
1048 /* A small optimization */
1049 if (texObj->MinFilter == eparam)
1050 return;
1051
1052 if (eparam==GL_NEAREST || eparam==GL_LINEAR) {
1053 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1054 texObj->MinFilter = eparam;
1055 }
1056 else if ((eparam==GL_NEAREST_MIPMAP_NEAREST ||
1057 eparam==GL_LINEAR_MIPMAP_NEAREST ||
1058 eparam==GL_NEAREST_MIPMAP_LINEAR ||
1059 eparam==GL_LINEAR_MIPMAP_LINEAR) &&
1060 texObj->Target != GL_TEXTURE_RECTANGLE_NV) {
1061 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1062 texObj->MinFilter = eparam;
1063 }
1064 else {
1065 _mesa_error( ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
1066 return;
1067 }
1068 break;
1069 case GL_TEXTURE_MAG_FILTER:
1070 /* A small optimization */
1071 if (texObj->MagFilter == eparam)
1072 return;
1073
1074 if (eparam==GL_NEAREST || eparam==GL_LINEAR) {
1075 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1076 texObj->MagFilter = eparam;
1077 }
1078 else {
1079 _mesa_error( ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
1080 return;
1081 }
1082 break;
1083 case GL_TEXTURE_WRAP_S:
1084 if (texObj->WrapS == eparam)
1085 return;
1086 if (eparam == GL_CLAMP || eparam == GL_CLAMP_TO_EDGE ||
1087 (eparam == GL_CLAMP_TO_BORDER_ARB &&
1088 ctx->Extensions.ARB_texture_border_clamp)) {
1089 /* any texture target */
1090 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1091 texObj->WrapS = eparam;
1092 }
1093 else if (texObj->Target != GL_TEXTURE_RECTANGLE_NV &&
1094 (eparam == GL_REPEAT ||
1095 (eparam == GL_MIRRORED_REPEAT_ARB &&
1096 ctx->Extensions.ARB_texture_mirrored_repeat))) {
1097 /* non-rectangle texture */
1098 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1099 texObj->WrapS = eparam;
1100 }
1101 else {
1102 _mesa_error( ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
1103 return;
1104 }
1105 break;
1106 case GL_TEXTURE_WRAP_T:
1107 if (texObj->WrapT == eparam)
1108 return;
1109 if (eparam == GL_CLAMP || eparam == GL_CLAMP_TO_EDGE ||
1110 (eparam == GL_CLAMP_TO_BORDER_ARB &&
1111 ctx->Extensions.ARB_texture_border_clamp)) {
1112 /* any texture target */
1113 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1114 texObj->WrapT = eparam;
1115 }
1116 else if (texObj->Target != GL_TEXTURE_RECTANGLE_NV &&
1117 (eparam == GL_REPEAT ||
1118 (eparam == GL_MIRRORED_REPEAT_ARB &&
1119 ctx->Extensions.ARB_texture_mirrored_repeat))) {
1120 /* non-rectangle texture */
1121 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1122 texObj->WrapT = eparam;
1123 }
1124 else {
1125 _mesa_error( ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
1126 return;
1127 }
1128 break;
1129 case GL_TEXTURE_WRAP_R_EXT:
1130 if (texObj->WrapR == eparam)
1131 return;
1132 if (eparam == GL_CLAMP || eparam == GL_CLAMP_TO_EDGE ||
1133 (eparam == GL_CLAMP_TO_BORDER_ARB &&
1134 ctx->Extensions.ARB_texture_border_clamp)) {
1135 /* any texture target */
1136 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1137 texObj->WrapR = eparam;
1138 }
1139 else if (texObj->Target != GL_TEXTURE_RECTANGLE_NV &&
1140 (eparam == GL_REPEAT ||
1141 (eparam == GL_MIRRORED_REPEAT_ARB &&
1142 ctx->Extensions.ARB_texture_mirrored_repeat))) {
1143 /* non-rectangle texture */
1144 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1145 texObj->WrapR = eparam;
1146 }
1147 else {
1148 _mesa_error( ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
1149 }
1150 break;
1151 #if 0 /* someday */
1152 case GL_TEXTUER_BORDER_VALUES_NV:
1153 /* don't clamp */
1154 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1155 COPY_4V(texObj->BorderValues, params);
1156 UNCLAMPED_FLOAT_TO_CHAN(texObj->BorderColor[0], params[0]);
1157 UNCLAMPED_FLOAT_TO_CHAN(texObj->BorderColor[1], params[1]);
1158 UNCLAMPED_FLOAT_TO_CHAN(texObj->BorderColor[2], params[2]);
1159 UNCLAMPED_FLOAT_TO_CHAN(texObj->BorderColor[3], params[3]);
1160 break;
1161 #endif
1162 case GL_TEXTURE_BORDER_COLOR:
1163 /* clamp */
1164 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1165 texObj->BorderValues[0] = CLAMP(params[0], 0.0F, 1.0F);
1166 texObj->BorderValues[1] = CLAMP(params[1], 0.0F, 1.0F);
1167 texObj->BorderValues[2] = CLAMP(params[2], 0.0F, 1.0F);
1168 texObj->BorderValues[3] = CLAMP(params[3], 0.0F, 1.0F);
1169 UNCLAMPED_FLOAT_TO_CHAN(texObj->BorderColor[0], texObj->BorderValues[0]);
1170 UNCLAMPED_FLOAT_TO_CHAN(texObj->BorderColor[1], texObj->BorderValues[1]);
1171 UNCLAMPED_FLOAT_TO_CHAN(texObj->BorderColor[2], texObj->BorderValues[2]);
1172 UNCLAMPED_FLOAT_TO_CHAN(texObj->BorderColor[3], texObj->BorderValues[3]);
1173 break;
1174 case GL_TEXTURE_MIN_LOD:
1175 if (texObj->MinLod == params[0])
1176 return;
1177 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1178 texObj->MinLod = params[0];
1179 break;
1180 case GL_TEXTURE_MAX_LOD:
1181 if (texObj->MaxLod == params[0])
1182 return;
1183 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1184 texObj->MaxLod = params[0];
1185 break;
1186 case GL_TEXTURE_BASE_LEVEL:
1187 if (params[0] < 0.0) {
1188 _mesa_error(ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
1189 return;
1190 }
1191 if (target == GL_TEXTURE_RECTANGLE_NV && params[0] != 0.0) {
1192 _mesa_error(ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
1193 return;
1194 }
1195 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1196 texObj->BaseLevel = (GLint) params[0];
1197 break;
1198 case GL_TEXTURE_MAX_LEVEL:
1199 if (params[0] < 0.0) {
1200 _mesa_error(ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
1201 return;
1202 }
1203 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1204 texObj->MaxLevel = (GLint) params[0];
1205 break;
1206 case GL_TEXTURE_PRIORITY:
1207 /* (keithh@netcomuk.co.uk) */
1208 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1209 texObj->Priority = CLAMP( params[0], 0.0F, 1.0F );
1210 break;
1211 case GL_TEXTURE_MAX_ANISOTROPY_EXT:
1212 if (ctx->Extensions.EXT_texture_filter_anisotropic) {
1213 if (params[0] < 1.0) {
1214 _mesa_error(ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
1215 return;
1216 }
1217 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1218 texObj->MaxAnisotropy = params[0];
1219 }
1220 else {
1221 _mesa_error(ctx, GL_INVALID_ENUM,
1222 "glTexParameter(pname=GL_MAX_TEXTURE_ANISOTROPY_EXT)");
1223 return;
1224 }
1225 break;
1226 case GL_TEXTURE_COMPARE_SGIX:
1227 if (ctx->Extensions.SGIX_shadow) {
1228 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1229 texObj->CompareFlag = params[0] ? GL_TRUE : GL_FALSE;
1230 }
1231 else {
1232 _mesa_error(ctx, GL_INVALID_ENUM,
1233 "glTexParameter(pname=GL_TEXTURE_COMPARE_SGIX)");
1234 return;
1235 }
1236 break;
1237 case GL_TEXTURE_COMPARE_OPERATOR_SGIX:
1238 if (ctx->Extensions.SGIX_shadow) {
1239 GLenum op = (GLenum) params[0];
1240 if (op == GL_TEXTURE_LEQUAL_R_SGIX ||
1241 op == GL_TEXTURE_GEQUAL_R_SGIX) {
1242 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1243 texObj->CompareOperator = op;
1244 }
1245 else {
1246 _mesa_error(ctx, GL_INVALID_ENUM, "glTexParameter(param)");
1247 }
1248 }
1249 else {
1250 _mesa_error(ctx, GL_INVALID_ENUM,
1251 "glTexParameter(pname=GL_TEXTURE_COMPARE_OPERATOR_SGIX)");
1252 return;
1253 }
1254 break;
1255 case GL_SHADOW_AMBIENT_SGIX: /* aka GL_TEXTURE_COMPARE_FAIL_VALUE_ARB */
1256 if (ctx->Extensions.SGIX_shadow_ambient) {
1257 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1258 UNCLAMPED_FLOAT_TO_CHAN(texObj->ShadowAmbient, params[0]);
1259 }
1260 else {
1261 _mesa_error(ctx, GL_INVALID_ENUM,
1262 "glTexParameter(pname=GL_SHADOW_AMBIENT_SGIX)");
1263 return;
1264 }
1265 break;
1266 case GL_GENERATE_MIPMAP_SGIS:
1267 if (ctx->Extensions.SGIS_generate_mipmap) {
1268 texObj->GenerateMipmap = params[0] ? GL_TRUE : GL_FALSE;
1269 }
1270 else {
1271 _mesa_error(ctx, GL_INVALID_ENUM,
1272 "glTexParameter(pname=GL_GENERATE_MIPMAP_SGIS)");
1273 return;
1274 }
1275 break;
1276 case GL_TEXTURE_COMPARE_MODE_ARB:
1277 if (ctx->Extensions.ARB_shadow) {
1278 const GLenum mode = (GLenum) params[0];
1279 if (mode == GL_NONE || mode == GL_COMPARE_R_TO_TEXTURE_ARB) {
1280 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1281 texObj->CompareMode = mode;
1282 }
1283 else {
1284 _mesa_error(ctx, GL_INVALID_ENUM,
1285 "glTexParameter(bad GL_TEXTURE_COMPARE_MODE_ARB)");
1286 return;
1287 }
1288 }
1289 else {
1290 _mesa_error(ctx, GL_INVALID_ENUM,
1291 "glTexParameter(pname=GL_TEXTURE_COMPARE_MODE_ARB)");
1292 return;
1293 }
1294 break;
1295 case GL_TEXTURE_COMPARE_FUNC_ARB:
1296 if (ctx->Extensions.ARB_shadow) {
1297 const GLenum func = (GLenum) params[0];
1298 if (func == GL_LEQUAL || func == GL_GEQUAL) {
1299 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1300 texObj->CompareFunc = func;
1301 }
1302 else if (ctx->Extensions.EXT_shadow_funcs &&
1303 (func == GL_EQUAL ||
1304 func == GL_NOTEQUAL ||
1305 func == GL_LESS ||
1306 func == GL_GREATER ||
1307 func == GL_ALWAYS ||
1308 func == GL_NEVER)) {
1309 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1310 texObj->CompareFunc = func;
1311 }
1312 else {
1313 _mesa_error(ctx, GL_INVALID_ENUM,
1314 "glTexParameter(bad GL_TEXTURE_COMPARE_FUNC_ARB)");
1315 return;
1316 }
1317 }
1318 else {
1319 _mesa_error(ctx, GL_INVALID_ENUM,
1320 "glTexParameter(pname=GL_TEXTURE_COMPARE_FUNC_ARB)");
1321 return;
1322 }
1323 break;
1324 case GL_DEPTH_TEXTURE_MODE_ARB:
1325 if (ctx->Extensions.ARB_depth_texture) {
1326 const GLenum result = (GLenum) params[0];
1327 if (result == GL_LUMINANCE || result == GL_INTENSITY
1328 || result == GL_ALPHA) {
1329 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1330 texObj->DepthMode = result;
1331 }
1332 else {
1333 _mesa_error(ctx, GL_INVALID_ENUM,
1334 "glTexParameter(bad GL_DEPTH_TEXTURE_MODE_ARB)");
1335 return;
1336 }
1337 }
1338 else {
1339 _mesa_error(ctx, GL_INVALID_ENUM,
1340 "glTexParameter(pname=GL_DEPTH_TEXTURE_MODE_ARB)");
1341 return;
1342 }
1343 break;
1344
1345 default:
1346 _mesa_error(ctx, GL_INVALID_ENUM,
1347 "glTexParameter(pname=0x%x)", pname);
1348 return;
1349 }
1350
1351 texObj->Complete = GL_FALSE;
1352
1353 if (ctx->Driver.TexParameter) {
1354 (*ctx->Driver.TexParameter)( ctx, target, texObj, pname, params );
1355 }
1356 }
1357
1358
1359 void
1360 _mesa_TexParameteri( GLenum target, GLenum pname, GLint param )
1361 {
1362 GLfloat fparam[4];
1363 fparam[0] = (GLfloat) param;
1364 fparam[1] = fparam[2] = fparam[3] = 0.0;
1365 _mesa_TexParameterfv(target, pname, fparam);
1366 }
1367
1368 void
1369 _mesa_TexParameteriv( GLenum target, GLenum pname, const GLint *params )
1370 {
1371 GLfloat fparam[4];
1372 fparam[0] = (GLfloat) params[0];
1373 fparam[1] = fparam[2] = fparam[3] = 0.0;
1374 _mesa_TexParameterfv(target, pname, fparam);
1375 }
1376
1377
1378 void
1379 _mesa_GetTexLevelParameterfv( GLenum target, GLint level,
1380 GLenum pname, GLfloat *params )
1381 {
1382 GLint iparam;
1383 _mesa_GetTexLevelParameteriv( target, level, pname, &iparam );
1384 *params = (GLfloat) iparam;
1385 }
1386
1387
1388 static GLuint
1389 tex_image_dimensions(GLcontext *ctx, GLenum target)
1390 {
1391 switch (target) {
1392 case GL_TEXTURE_1D:
1393 case GL_PROXY_TEXTURE_1D:
1394 return 1;
1395 case GL_TEXTURE_2D:
1396 case GL_PROXY_TEXTURE_2D:
1397 return 2;
1398 case GL_TEXTURE_3D:
1399 case GL_PROXY_TEXTURE_3D:
1400 return 3;
1401 case GL_TEXTURE_CUBE_MAP_ARB:
1402 case GL_PROXY_TEXTURE_CUBE_MAP_ARB:
1403 case GL_TEXTURE_CUBE_MAP_POSITIVE_X_ARB:
1404 case GL_TEXTURE_CUBE_MAP_NEGATIVE_X_ARB:
1405 case GL_TEXTURE_CUBE_MAP_POSITIVE_Y_ARB:
1406 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y_ARB:
1407 case GL_TEXTURE_CUBE_MAP_POSITIVE_Z_ARB:
1408 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z_ARB:
1409 return ctx->Extensions.ARB_texture_cube_map ? 2 : 0;
1410 case GL_TEXTURE_RECTANGLE_NV:
1411 case GL_PROXY_TEXTURE_RECTANGLE_NV:
1412 return ctx->Extensions.NV_texture_rectangle ? 2 : 0;
1413 default:
1414 _mesa_problem(ctx, "bad target in _mesa_tex_target_dimensions()");
1415 return 0;
1416 }
1417 }
1418
1419
1420 void
1421 _mesa_GetTexLevelParameteriv( GLenum target, GLint level,
1422 GLenum pname, GLint *params )
1423 {
1424 GET_CURRENT_CONTEXT(ctx);
1425 const struct gl_texture_unit *texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
1426 const struct gl_texture_image *img = NULL;
1427 GLuint dimensions;
1428 GLboolean isProxy;
1429 GLint maxLevels;
1430 ASSERT_OUTSIDE_BEGIN_END(ctx);
1431
1432 /* this will catch bad target values */
1433 dimensions = tex_image_dimensions(ctx, target); /* 1, 2 or 3 */
1434 if (dimensions == 0) {
1435 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexLevelParameter[if]v(target)");
1436 return;
1437 }
1438
1439 switch (target) {
1440 case GL_TEXTURE_1D:
1441 case GL_PROXY_TEXTURE_1D:
1442 case GL_TEXTURE_2D:
1443 case GL_PROXY_TEXTURE_2D:
1444 maxLevels = ctx->Const.MaxTextureLevels;
1445 break;
1446 case GL_TEXTURE_3D:
1447 case GL_PROXY_TEXTURE_3D:
1448 maxLevels = ctx->Const.Max3DTextureLevels;
1449 break;
1450 case GL_TEXTURE_CUBE_MAP_POSITIVE_X_ARB:
1451 case GL_TEXTURE_CUBE_MAP_NEGATIVE_X_ARB:
1452 case GL_TEXTURE_CUBE_MAP_POSITIVE_Y_ARB:
1453 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y_ARB:
1454 case GL_TEXTURE_CUBE_MAP_POSITIVE_Z_ARB:
1455 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z_ARB:
1456 case GL_PROXY_TEXTURE_CUBE_MAP_ARB:
1457 maxLevels = ctx->Const.MaxCubeTextureLevels;
1458 break;
1459 case GL_TEXTURE_RECTANGLE_NV:
1460 case GL_PROXY_TEXTURE_RECTANGLE_NV:
1461 maxLevels = 1;
1462 break;
1463 default:
1464 _mesa_problem(ctx, "switch in _mesa_GetTexLevelParameter");
1465 return;
1466 }
1467
1468 if (level < 0 || level >= maxLevels) {
1469 _mesa_error( ctx, GL_INVALID_VALUE, "glGetTexLevelParameter[if]v" );
1470 return;
1471 }
1472
1473 img = _mesa_select_tex_image(ctx, texUnit, target, level);
1474 if (!img || !img->TexFormat) {
1475 /* undefined texture image */
1476 if (pname == GL_TEXTURE_COMPONENTS)
1477 *params = 1;
1478 else
1479 *params = 0;
1480 return;
1481 }
1482
1483 isProxy = (target == GL_PROXY_TEXTURE_1D) ||
1484 (target == GL_PROXY_TEXTURE_2D) ||
1485 (target == GL_PROXY_TEXTURE_3D) ||
1486 (target == GL_PROXY_TEXTURE_CUBE_MAP_ARB) ||
1487 (target == GL_PROXY_TEXTURE_RECTANGLE_NV);
1488
1489 switch (pname) {
1490 case GL_TEXTURE_WIDTH:
1491 *params = img->Width;
1492 return;
1493 case GL_TEXTURE_HEIGHT:
1494 *params = img->Height;
1495 return;
1496 case GL_TEXTURE_DEPTH:
1497 *params = img->Depth;
1498 return;
1499 case GL_TEXTURE_INTERNAL_FORMAT:
1500 *params = img->IntFormat;
1501 return;
1502 case GL_TEXTURE_BORDER:
1503 *params = img->Border;
1504 return;
1505 case GL_TEXTURE_RED_SIZE:
1506 if (img->Format == GL_RGB || img->Format == GL_RGBA)
1507 *params = img->TexFormat->RedBits;
1508 else
1509 *params = 0;
1510 return;
1511 case GL_TEXTURE_GREEN_SIZE:
1512 if (img->Format == GL_RGB || img->Format == GL_RGBA)
1513 *params = img->TexFormat->GreenBits;
1514 else
1515 *params = 0;
1516 return;
1517 case GL_TEXTURE_BLUE_SIZE:
1518 if (img->Format == GL_RGB || img->Format == GL_RGBA)
1519 *params = img->TexFormat->BlueBits;
1520 else
1521 *params = 0;
1522 return;
1523 case GL_TEXTURE_ALPHA_SIZE:
1524 if (img->Format == GL_ALPHA || img->Format == GL_LUMINANCE_ALPHA ||
1525 img->Format == GL_RGBA)
1526 *params = img->TexFormat->AlphaBits;
1527 else
1528 *params = 0;
1529 return;
1530 case GL_TEXTURE_INTENSITY_SIZE:
1531 if (img->Format != GL_INTENSITY)
1532 *params = 0;
1533 else if (img->TexFormat->IntensityBits > 0)
1534 *params = img->TexFormat->IntensityBits;
1535 else /* intensity probably stored as rgb texture */
1536 *params = MIN2(img->TexFormat->RedBits, img->TexFormat->GreenBits);
1537 return;
1538 case GL_TEXTURE_LUMINANCE_SIZE:
1539 if (img->Format != GL_LUMINANCE &&
1540 img->Format != GL_LUMINANCE_ALPHA)
1541 *params = 0;
1542 else if (img->TexFormat->LuminanceBits > 0)
1543 *params = img->TexFormat->LuminanceBits;
1544 else /* luminance probably stored as rgb texture */
1545 *params = MIN2(img->TexFormat->RedBits, img->TexFormat->GreenBits);
1546 return;
1547 case GL_TEXTURE_INDEX_SIZE_EXT:
1548 if (img->Format == GL_COLOR_INDEX)
1549 *params = img->TexFormat->IndexBits;
1550 else
1551 *params = 0;
1552 return;
1553 case GL_DEPTH_BITS:
1554 /* XXX this isn't in the GL_SGIX_depth_texture spec
1555 * but seems appropriate.
1556 */
1557 if (ctx->Extensions.SGIX_depth_texture)
1558 *params = img->TexFormat->DepthBits;
1559 else
1560 _mesa_error(ctx, GL_INVALID_ENUM,
1561 "glGetTexLevelParameter[if]v(pname)");
1562 return;
1563
1564 /* GL_ARB_texture_compression */
1565 case GL_TEXTURE_COMPRESSED_IMAGE_SIZE_ARB:
1566 if (ctx->Extensions.ARB_texture_compression) {
1567 if (img->IsCompressed && !isProxy)
1568 *params = img->CompressedSize;
1569 else
1570 _mesa_error(ctx, GL_INVALID_OPERATION,
1571 "glGetTexLevelParameter[if]v(pname)");
1572 }
1573 else {
1574 _mesa_error(ctx, GL_INVALID_ENUM,
1575 "glGetTexLevelParameter[if]v(pname)");
1576 }
1577 return;
1578 case GL_TEXTURE_COMPRESSED_ARB:
1579 if (ctx->Extensions.ARB_texture_compression) {
1580 *params = (GLint) img->IsCompressed;
1581 }
1582 else {
1583 _mesa_error(ctx, GL_INVALID_ENUM,
1584 "glGetTexLevelParameter[if]v(pname)");
1585 }
1586 return;
1587
1588 default:
1589 _mesa_error(ctx, GL_INVALID_ENUM,
1590 "glGetTexLevelParameter[if]v(pname)");
1591 }
1592 }
1593
1594
1595
1596 void
1597 _mesa_GetTexParameterfv( GLenum target, GLenum pname, GLfloat *params )
1598 {
1599 GET_CURRENT_CONTEXT(ctx);
1600 struct gl_texture_unit *texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
1601 struct gl_texture_object *obj;
1602 ASSERT_OUTSIDE_BEGIN_END(ctx);
1603
1604 obj = _mesa_select_tex_object(ctx, texUnit, target);
1605 if (!obj) {
1606 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexParameterfv(target)");
1607 return;
1608 }
1609
1610 switch (pname) {
1611 case GL_TEXTURE_MAG_FILTER:
1612 *params = ENUM_TO_FLOAT(obj->MagFilter);
1613 return;
1614 case GL_TEXTURE_MIN_FILTER:
1615 *params = ENUM_TO_FLOAT(obj->MinFilter);
1616 return;
1617 case GL_TEXTURE_WRAP_S:
1618 *params = ENUM_TO_FLOAT(obj->WrapS);
1619 return;
1620 case GL_TEXTURE_WRAP_T:
1621 *params = ENUM_TO_FLOAT(obj->WrapT);
1622 return;
1623 case GL_TEXTURE_WRAP_R_EXT:
1624 *params = ENUM_TO_FLOAT(obj->WrapR);
1625 return;
1626 #if 0 /* someday */
1627 case GL_TEXTURE_BORDER_VALUES_NV:
1628 /* unclamped */
1629 params[0] = obj->BorderValues[0];
1630 params[1] = obj->BorderValues[1];
1631 params[2] = obj->BorderValues[2];
1632 params[3] = obj->BorderValues[3];
1633 return;
1634 #endif
1635 case GL_TEXTURE_BORDER_COLOR:
1636 /* clamped */
1637 params[0] = obj->BorderColor[0] / CHAN_MAXF;
1638 params[1] = obj->BorderColor[1] / CHAN_MAXF;
1639 params[2] = obj->BorderColor[2] / CHAN_MAXF;
1640 params[3] = obj->BorderColor[3] / CHAN_MAXF;
1641 return;
1642 case GL_TEXTURE_RESIDENT:
1643 {
1644 GLboolean resident;
1645 if (ctx->Driver.IsTextureResident)
1646 resident = ctx->Driver.IsTextureResident(ctx, obj);
1647 else
1648 resident = GL_TRUE;
1649 *params = ENUM_TO_FLOAT(resident);
1650 }
1651 return;
1652 case GL_TEXTURE_PRIORITY:
1653 *params = obj->Priority;
1654 return;
1655 case GL_TEXTURE_MIN_LOD:
1656 *params = obj->MinLod;
1657 return;
1658 case GL_TEXTURE_MAX_LOD:
1659 *params = obj->MaxLod;
1660 return;
1661 case GL_TEXTURE_BASE_LEVEL:
1662 *params = (GLfloat) obj->BaseLevel;
1663 return;
1664 case GL_TEXTURE_MAX_LEVEL:
1665 *params = (GLfloat) obj->MaxLevel;
1666 return;
1667 case GL_TEXTURE_MAX_ANISOTROPY_EXT:
1668 if (ctx->Extensions.EXT_texture_filter_anisotropic) {
1669 *params = obj->MaxAnisotropy;
1670 return;
1671 }
1672 break;
1673 case GL_TEXTURE_COMPARE_SGIX:
1674 if (ctx->Extensions.SGIX_shadow) {
1675 *params = (GLfloat) obj->CompareFlag;
1676 return;
1677 }
1678 break;
1679 case GL_TEXTURE_COMPARE_OPERATOR_SGIX:
1680 if (ctx->Extensions.SGIX_shadow) {
1681 *params = (GLfloat) obj->CompareOperator;
1682 return;
1683 }
1684 break;
1685 case GL_SHADOW_AMBIENT_SGIX: /* aka GL_TEXTURE_COMPARE_FAIL_VALUE_ARB */
1686 if (ctx->Extensions.SGIX_shadow_ambient) {
1687 *params = CHAN_TO_FLOAT(obj->ShadowAmbient);
1688 return;
1689 }
1690 break;
1691 case GL_GENERATE_MIPMAP_SGIS:
1692 if (ctx->Extensions.SGIS_generate_mipmap) {
1693 *params = (GLfloat) obj->GenerateMipmap;
1694 return;
1695 }
1696 break;
1697 case GL_TEXTURE_COMPARE_MODE_ARB:
1698 if (ctx->Extensions.ARB_shadow) {
1699 *params = (GLfloat) obj->CompareMode;
1700 return;
1701 }
1702 break;
1703 case GL_TEXTURE_COMPARE_FUNC_ARB:
1704 if (ctx->Extensions.ARB_shadow) {
1705 *params = (GLfloat) obj->CompareFunc;
1706 return;
1707 }
1708 break;
1709 case GL_DEPTH_TEXTURE_MODE_ARB:
1710 if (ctx->Extensions.ARB_depth_texture) {
1711 *params = (GLfloat) obj->DepthMode;
1712 return;
1713 }
1714 break;
1715 default:
1716 ; /* silence warnings */
1717 }
1718 /* If we get here, pname was an unrecognized enum */
1719 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexParameterfv(pname)" );
1720 }
1721
1722
1723 void
1724 _mesa_GetTexParameteriv( GLenum target, GLenum pname, GLint *params )
1725 {
1726 GET_CURRENT_CONTEXT(ctx);
1727 struct gl_texture_unit *texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
1728 struct gl_texture_object *obj;
1729 ASSERT_OUTSIDE_BEGIN_END(ctx);
1730
1731 obj = _mesa_select_tex_object(ctx, texUnit, target);
1732 if (!obj) {
1733 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexParameteriv(target)");
1734 return;
1735 }
1736
1737 switch (pname) {
1738 case GL_TEXTURE_MAG_FILTER:
1739 *params = (GLint) obj->MagFilter;
1740 return;
1741 case GL_TEXTURE_MIN_FILTER:
1742 *params = (GLint) obj->MinFilter;
1743 return;
1744 case GL_TEXTURE_WRAP_S:
1745 *params = (GLint) obj->WrapS;
1746 return;
1747 case GL_TEXTURE_WRAP_T:
1748 *params = (GLint) obj->WrapT;
1749 return;
1750 case GL_TEXTURE_WRAP_R_EXT:
1751 *params = (GLint) obj->WrapR;
1752 return;
1753 #if 0 /* someday */
1754 case GL_TEXTURE_BORDER_VALUES_NV:
1755 /* unclamped */
1756 params[0] = FLOAT_TO_INT(obj->BorderValues[0]);
1757 params[1] = FLOAT_TO_INT(obj->BorderValues[1]);
1758 params[2] = FLOAT_TO_INT(obj->BorderValues[2]);
1759 params[3] = FLOAT_TO_INT(obj->BorderValues[3]);
1760 return;
1761 #endif
1762 case GL_TEXTURE_BORDER_COLOR:
1763 /* clamped */
1764 {
1765 GLfloat b[4];
1766 b[0] = CLAMP(obj->BorderValues[0], 0.0F, 1.0F);
1767 b[1] = CLAMP(obj->BorderValues[1], 0.0F, 1.0F);
1768 b[2] = CLAMP(obj->BorderValues[2], 0.0F, 1.0F);
1769 b[3] = CLAMP(obj->BorderValues[3], 0.0F, 1.0F);
1770 params[0] = FLOAT_TO_INT(b[0]);
1771 params[1] = FLOAT_TO_INT(b[1]);
1772 params[2] = FLOAT_TO_INT(b[2]);
1773 params[3] = FLOAT_TO_INT(b[3]);
1774 }
1775 return;
1776 case GL_TEXTURE_RESIDENT:
1777 {
1778 GLboolean resident;
1779 if (ctx->Driver.IsTextureResident)
1780 resident = ctx->Driver.IsTextureResident(ctx, obj);
1781 else
1782 resident = GL_TRUE;
1783 *params = (GLint) resident;
1784 }
1785 return;
1786 case GL_TEXTURE_PRIORITY:
1787 *params = (GLint) obj->Priority;
1788 return;
1789 case GL_TEXTURE_MIN_LOD:
1790 *params = (GLint) obj->MinLod;
1791 return;
1792 case GL_TEXTURE_MAX_LOD:
1793 *params = (GLint) obj->MaxLod;
1794 return;
1795 case GL_TEXTURE_BASE_LEVEL:
1796 *params = obj->BaseLevel;
1797 return;
1798 case GL_TEXTURE_MAX_LEVEL:
1799 *params = obj->MaxLevel;
1800 return;
1801 case GL_TEXTURE_MAX_ANISOTROPY_EXT:
1802 if (ctx->Extensions.EXT_texture_filter_anisotropic) {
1803 *params = (GLint) obj->MaxAnisotropy;
1804 return;
1805 }
1806 break;
1807 case GL_TEXTURE_COMPARE_SGIX:
1808 if (ctx->Extensions.SGIX_shadow) {
1809 *params = (GLint) obj->CompareFlag;
1810 return;
1811 }
1812 break;
1813 case GL_TEXTURE_COMPARE_OPERATOR_SGIX:
1814 if (ctx->Extensions.SGIX_shadow) {
1815 *params = (GLint) obj->CompareOperator;
1816 return;
1817 }
1818 break;
1819 case GL_SHADOW_AMBIENT_SGIX: /* aka GL_TEXTURE_COMPARE_FAIL_VALUE_ARB */
1820 if (ctx->Extensions.SGIX_shadow_ambient) {
1821 GLfloat a = CHAN_TO_FLOAT(obj->ShadowAmbient);
1822 *params = (GLint) FLOAT_TO_INT(a);
1823 return;
1824 }
1825 break;
1826 case GL_GENERATE_MIPMAP_SGIS:
1827 if (ctx->Extensions.SGIS_generate_mipmap) {
1828 *params = (GLint) obj->GenerateMipmap;
1829 return;
1830 }
1831 break;
1832 case GL_TEXTURE_COMPARE_MODE_ARB:
1833 if (ctx->Extensions.ARB_shadow) {
1834 *params = (GLint) obj->CompareMode;
1835 return;
1836 }
1837 break;
1838 case GL_TEXTURE_COMPARE_FUNC_ARB:
1839 if (ctx->Extensions.ARB_shadow) {
1840 *params = (GLint) obj->CompareFunc;
1841 return;
1842 }
1843 break;
1844 case GL_DEPTH_TEXTURE_MODE_ARB:
1845 if (ctx->Extensions.ARB_depth_texture) {
1846 *params = (GLint) obj->DepthMode;
1847 return;
1848 }
1849 break;
1850 default:
1851 ; /* silence warnings */
1852 }
1853 /* If we get here, pname was an unrecognized enum */
1854 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexParameteriv(pname)" );
1855 }
1856
1857
1858
1859
1860 /**********************************************************************/
1861 /* Texture Coord Generation */
1862 /**********************************************************************/
1863
1864
1865 void
1866 _mesa_TexGenfv( GLenum coord, GLenum pname, const GLfloat *params )
1867 {
1868 GET_CURRENT_CONTEXT(ctx);
1869 GLuint tUnit = ctx->Texture.CurrentUnit;
1870 struct gl_texture_unit *texUnit = &ctx->Texture.Unit[tUnit];
1871 ASSERT_OUTSIDE_BEGIN_END(ctx);
1872
1873 if (MESA_VERBOSE&(VERBOSE_API|VERBOSE_TEXTURE))
1874 _mesa_debug(ctx, "texGEN %s %s %x...\n",
1875 _mesa_lookup_enum_by_nr(coord),
1876 _mesa_lookup_enum_by_nr(pname),
1877 *(int *)params);
1878
1879 switch (coord) {
1880 case GL_S:
1881 if (pname==GL_TEXTURE_GEN_MODE) {
1882 GLenum mode = (GLenum) (GLint) *params;
1883 GLuint bits;
1884 switch (mode) {
1885 case GL_OBJECT_LINEAR:
1886 bits = TEXGEN_OBJ_LINEAR;
1887 break;
1888 case GL_EYE_LINEAR:
1889 bits = TEXGEN_EYE_LINEAR;
1890 break;
1891 case GL_REFLECTION_MAP_NV:
1892 bits = TEXGEN_REFLECTION_MAP_NV;
1893 break;
1894 case GL_NORMAL_MAP_NV:
1895 bits = TEXGEN_NORMAL_MAP_NV;
1896 break;
1897 case GL_SPHERE_MAP:
1898 bits = TEXGEN_SPHERE_MAP;
1899 break;
1900 default:
1901 _mesa_error( ctx, GL_INVALID_ENUM, "glTexGenfv(param)" );
1902 return;
1903 }
1904 if (texUnit->GenModeS == mode)
1905 return;
1906 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1907 texUnit->GenModeS = mode;
1908 texUnit->_GenBitS = bits;
1909 }
1910 else if (pname==GL_OBJECT_PLANE) {
1911 if (TEST_EQ_4V(texUnit->ObjectPlaneS, params))
1912 return;
1913 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1914 texUnit->ObjectPlaneS[0] = params[0];
1915 texUnit->ObjectPlaneS[1] = params[1];
1916 texUnit->ObjectPlaneS[2] = params[2];
1917 texUnit->ObjectPlaneS[3] = params[3];
1918 }
1919 else if (pname==GL_EYE_PLANE) {
1920 GLfloat tmp[4];
1921
1922 /* Transform plane equation by the inverse modelview matrix */
1923 if (ctx->ModelviewMatrixStack.Top->flags & MAT_DIRTY_INVERSE) {
1924 _math_matrix_analyse( ctx->ModelviewMatrixStack.Top );
1925 }
1926 _mesa_transform_vector( tmp, params, ctx->ModelviewMatrixStack.Top->inv );
1927 if (TEST_EQ_4V(texUnit->EyePlaneS, tmp))
1928 return;
1929 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1930 COPY_4FV(texUnit->EyePlaneS, tmp);
1931 }
1932 else {
1933 _mesa_error( ctx, GL_INVALID_ENUM, "glTexGenfv(pname)" );
1934 return;
1935 }
1936 break;
1937 case GL_T:
1938 if (pname==GL_TEXTURE_GEN_MODE) {
1939 GLenum mode = (GLenum) (GLint) *params;
1940 GLuint bitt;
1941 switch (mode) {
1942 case GL_OBJECT_LINEAR:
1943 bitt = TEXGEN_OBJ_LINEAR;
1944 break;
1945 case GL_EYE_LINEAR:
1946 bitt = TEXGEN_EYE_LINEAR;
1947 break;
1948 case GL_REFLECTION_MAP_NV:
1949 bitt = TEXGEN_REFLECTION_MAP_NV;
1950 break;
1951 case GL_NORMAL_MAP_NV:
1952 bitt = TEXGEN_NORMAL_MAP_NV;
1953 break;
1954 case GL_SPHERE_MAP:
1955 bitt = TEXGEN_SPHERE_MAP;
1956 break;
1957 default:
1958 _mesa_error( ctx, GL_INVALID_ENUM, "glTexGenfv(param)" );
1959 return;
1960 }
1961 if (texUnit->GenModeT == mode)
1962 return;
1963 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1964 texUnit->GenModeT = mode;
1965 texUnit->_GenBitT = bitt;
1966 }
1967 else if (pname==GL_OBJECT_PLANE) {
1968 if (TEST_EQ_4V(texUnit->ObjectPlaneT, params))
1969 return;
1970 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1971 texUnit->ObjectPlaneT[0] = params[0];
1972 texUnit->ObjectPlaneT[1] = params[1];
1973 texUnit->ObjectPlaneT[2] = params[2];
1974 texUnit->ObjectPlaneT[3] = params[3];
1975 }
1976 else if (pname==GL_EYE_PLANE) {
1977 GLfloat tmp[4];
1978 /* Transform plane equation by the inverse modelview matrix */
1979 if (ctx->ModelviewMatrixStack.Top->flags & MAT_DIRTY_INVERSE) {
1980 _math_matrix_analyse( ctx->ModelviewMatrixStack.Top );
1981 }
1982 _mesa_transform_vector( tmp, params, ctx->ModelviewMatrixStack.Top->inv );
1983 if (TEST_EQ_4V(texUnit->EyePlaneT, tmp))
1984 return;
1985 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
1986 COPY_4FV(texUnit->EyePlaneT, tmp);
1987 }
1988 else {
1989 _mesa_error( ctx, GL_INVALID_ENUM, "glTexGenfv(pname)" );
1990 return;
1991 }
1992 break;
1993 case GL_R:
1994 if (pname==GL_TEXTURE_GEN_MODE) {
1995 GLenum mode = (GLenum) (GLint) *params;
1996 GLuint bitr;
1997 switch (mode) {
1998 case GL_OBJECT_LINEAR:
1999 bitr = TEXGEN_OBJ_LINEAR;
2000 break;
2001 case GL_REFLECTION_MAP_NV:
2002 bitr = TEXGEN_REFLECTION_MAP_NV;
2003 break;
2004 case GL_NORMAL_MAP_NV:
2005 bitr = TEXGEN_NORMAL_MAP_NV;
2006 break;
2007 case GL_EYE_LINEAR:
2008 bitr = TEXGEN_EYE_LINEAR;
2009 break;
2010 default:
2011 _mesa_error( ctx, GL_INVALID_ENUM, "glTexGenfv(param)" );
2012 return;
2013 }
2014 if (texUnit->GenModeR == mode)
2015 return;
2016 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
2017 texUnit->GenModeR = mode;
2018 texUnit->_GenBitR = bitr;
2019 }
2020 else if (pname==GL_OBJECT_PLANE) {
2021 if (TEST_EQ_4V(texUnit->ObjectPlaneR, params))
2022 return;
2023 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
2024 texUnit->ObjectPlaneR[0] = params[0];
2025 texUnit->ObjectPlaneR[1] = params[1];
2026 texUnit->ObjectPlaneR[2] = params[2];
2027 texUnit->ObjectPlaneR[3] = params[3];
2028 }
2029 else if (pname==GL_EYE_PLANE) {
2030 GLfloat tmp[4];
2031 /* Transform plane equation by the inverse modelview matrix */
2032 if (ctx->ModelviewMatrixStack.Top->flags & MAT_DIRTY_INVERSE) {
2033 _math_matrix_analyse( ctx->ModelviewMatrixStack.Top );
2034 }
2035 _mesa_transform_vector( tmp, params, ctx->ModelviewMatrixStack.Top->inv );
2036 if (TEST_EQ_4V(texUnit->EyePlaneR, tmp))
2037 return;
2038 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
2039 COPY_4FV(texUnit->EyePlaneR, tmp);
2040 }
2041 else {
2042 _mesa_error( ctx, GL_INVALID_ENUM, "glTexGenfv(pname)" );
2043 return;
2044 }
2045 break;
2046 case GL_Q:
2047 if (pname==GL_TEXTURE_GEN_MODE) {
2048 GLenum mode = (GLenum) (GLint) *params;
2049 GLuint bitq;
2050 switch (mode) {
2051 case GL_OBJECT_LINEAR:
2052 bitq = TEXGEN_OBJ_LINEAR;
2053 break;
2054 case GL_EYE_LINEAR:
2055 bitq = TEXGEN_EYE_LINEAR;
2056 break;
2057 default:
2058 _mesa_error( ctx, GL_INVALID_ENUM, "glTexGenfv(param)" );
2059 return;
2060 }
2061 if (texUnit->GenModeQ == mode)
2062 return;
2063 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
2064 texUnit->GenModeQ = mode;
2065 texUnit->_GenBitQ = bitq;
2066 }
2067 else if (pname==GL_OBJECT_PLANE) {
2068 if (TEST_EQ_4V(texUnit->ObjectPlaneQ, params))
2069 return;
2070 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
2071 texUnit->ObjectPlaneQ[0] = params[0];
2072 texUnit->ObjectPlaneQ[1] = params[1];
2073 texUnit->ObjectPlaneQ[2] = params[2];
2074 texUnit->ObjectPlaneQ[3] = params[3];
2075 }
2076 else if (pname==GL_EYE_PLANE) {
2077 GLfloat tmp[4];
2078 /* Transform plane equation by the inverse modelview matrix */
2079 if (ctx->ModelviewMatrixStack.Top->flags & MAT_DIRTY_INVERSE) {
2080 _math_matrix_analyse( ctx->ModelviewMatrixStack.Top );
2081 }
2082 _mesa_transform_vector( tmp, params, ctx->ModelviewMatrixStack.Top->inv );
2083 if (TEST_EQ_4V(texUnit->EyePlaneQ, tmp))
2084 return;
2085 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
2086 COPY_4FV(texUnit->EyePlaneQ, tmp);
2087 }
2088 else {
2089 _mesa_error( ctx, GL_INVALID_ENUM, "glTexGenfv(pname)" );
2090 return;
2091 }
2092 break;
2093 default:
2094 _mesa_error( ctx, GL_INVALID_ENUM, "glTexGenfv(coord)" );
2095 return;
2096 }
2097
2098 if (ctx->Driver.TexGen)
2099 ctx->Driver.TexGen( ctx, coord, pname, params );
2100 }
2101
2102
2103 void
2104 _mesa_TexGeniv(GLenum coord, GLenum pname, const GLint *params )
2105 {
2106 GLfloat p[4];
2107 p[0] = (GLfloat) params[0];
2108 p[1] = (GLfloat) params[1];
2109 p[2] = (GLfloat) params[2];
2110 p[3] = (GLfloat) params[3];
2111 _mesa_TexGenfv(coord, pname, p);
2112 }
2113
2114
2115 void
2116 _mesa_TexGend(GLenum coord, GLenum pname, GLdouble param )
2117 {
2118 GLfloat p = (GLfloat) param;
2119 _mesa_TexGenfv( coord, pname, &p );
2120 }
2121
2122
2123 void
2124 _mesa_TexGendv(GLenum coord, GLenum pname, const GLdouble *params )
2125 {
2126 GLfloat p[4];
2127 p[0] = (GLfloat) params[0];
2128 p[1] = (GLfloat) params[1];
2129 p[2] = (GLfloat) params[2];
2130 p[3] = (GLfloat) params[3];
2131 _mesa_TexGenfv( coord, pname, p );
2132 }
2133
2134
2135 void
2136 _mesa_TexGenf( GLenum coord, GLenum pname, GLfloat param )
2137 {
2138 _mesa_TexGenfv(coord, pname, &param);
2139 }
2140
2141
2142 void
2143 _mesa_TexGeni( GLenum coord, GLenum pname, GLint param )
2144 {
2145 _mesa_TexGeniv( coord, pname, &param );
2146 }
2147
2148
2149
2150 void
2151 _mesa_GetTexGendv( GLenum coord, GLenum pname, GLdouble *params )
2152 {
2153 GET_CURRENT_CONTEXT(ctx);
2154 GLuint tUnit = ctx->Texture.CurrentUnit;
2155 struct gl_texture_unit *texUnit = &ctx->Texture.Unit[tUnit];
2156 ASSERT_OUTSIDE_BEGIN_END(ctx);
2157
2158 switch (coord) {
2159 case GL_S:
2160 if (pname==GL_TEXTURE_GEN_MODE) {
2161 params[0] = ENUM_TO_DOUBLE(texUnit->GenModeS);
2162 }
2163 else if (pname==GL_OBJECT_PLANE) {
2164 COPY_4V( params, texUnit->ObjectPlaneS );
2165 }
2166 else if (pname==GL_EYE_PLANE) {
2167 COPY_4V( params, texUnit->EyePlaneS );
2168 }
2169 else {
2170 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGendv(pname)" );
2171 return;
2172 }
2173 break;
2174 case GL_T:
2175 if (pname==GL_TEXTURE_GEN_MODE) {
2176 params[0] = ENUM_TO_DOUBLE(texUnit->GenModeT);
2177 }
2178 else if (pname==GL_OBJECT_PLANE) {
2179 COPY_4V( params, texUnit->ObjectPlaneT );
2180 }
2181 else if (pname==GL_EYE_PLANE) {
2182 COPY_4V( params, texUnit->EyePlaneT );
2183 }
2184 else {
2185 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGendv(pname)" );
2186 return;
2187 }
2188 break;
2189 case GL_R:
2190 if (pname==GL_TEXTURE_GEN_MODE) {
2191 params[0] = ENUM_TO_DOUBLE(texUnit->GenModeR);
2192 }
2193 else if (pname==GL_OBJECT_PLANE) {
2194 COPY_4V( params, texUnit->ObjectPlaneR );
2195 }
2196 else if (pname==GL_EYE_PLANE) {
2197 COPY_4V( params, texUnit->EyePlaneR );
2198 }
2199 else {
2200 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGendv(pname)" );
2201 return;
2202 }
2203 break;
2204 case GL_Q:
2205 if (pname==GL_TEXTURE_GEN_MODE) {
2206 params[0] = ENUM_TO_DOUBLE(texUnit->GenModeQ);
2207 }
2208 else if (pname==GL_OBJECT_PLANE) {
2209 COPY_4V( params, texUnit->ObjectPlaneQ );
2210 }
2211 else if (pname==GL_EYE_PLANE) {
2212 COPY_4V( params, texUnit->EyePlaneQ );
2213 }
2214 else {
2215 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGendv(pname)" );
2216 return;
2217 }
2218 break;
2219 default:
2220 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGendv(coord)" );
2221 return;
2222 }
2223 }
2224
2225
2226
2227 void
2228 _mesa_GetTexGenfv( GLenum coord, GLenum pname, GLfloat *params )
2229 {
2230 GET_CURRENT_CONTEXT(ctx);
2231 GLuint tUnit = ctx->Texture.CurrentUnit;
2232 struct gl_texture_unit *texUnit = &ctx->Texture.Unit[tUnit];
2233 ASSERT_OUTSIDE_BEGIN_END(ctx);
2234
2235 switch (coord) {
2236 case GL_S:
2237 if (pname==GL_TEXTURE_GEN_MODE) {
2238 params[0] = ENUM_TO_FLOAT(texUnit->GenModeS);
2239 }
2240 else if (pname==GL_OBJECT_PLANE) {
2241 COPY_4V( params, texUnit->ObjectPlaneS );
2242 }
2243 else if (pname==GL_EYE_PLANE) {
2244 COPY_4V( params, texUnit->EyePlaneS );
2245 }
2246 else {
2247 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGenfv(pname)" );
2248 return;
2249 }
2250 break;
2251 case GL_T:
2252 if (pname==GL_TEXTURE_GEN_MODE) {
2253 params[0] = ENUM_TO_FLOAT(texUnit->GenModeT);
2254 }
2255 else if (pname==GL_OBJECT_PLANE) {
2256 COPY_4V( params, texUnit->ObjectPlaneT );
2257 }
2258 else if (pname==GL_EYE_PLANE) {
2259 COPY_4V( params, texUnit->EyePlaneT );
2260 }
2261 else {
2262 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGenfv(pname)" );
2263 return;
2264 }
2265 break;
2266 case GL_R:
2267 if (pname==GL_TEXTURE_GEN_MODE) {
2268 params[0] = ENUM_TO_FLOAT(texUnit->GenModeR);
2269 }
2270 else if (pname==GL_OBJECT_PLANE) {
2271 COPY_4V( params, texUnit->ObjectPlaneR );
2272 }
2273 else if (pname==GL_EYE_PLANE) {
2274 COPY_4V( params, texUnit->EyePlaneR );
2275 }
2276 else {
2277 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGenfv(pname)" );
2278 return;
2279 }
2280 break;
2281 case GL_Q:
2282 if (pname==GL_TEXTURE_GEN_MODE) {
2283 params[0] = ENUM_TO_FLOAT(texUnit->GenModeQ);
2284 }
2285 else if (pname==GL_OBJECT_PLANE) {
2286 COPY_4V( params, texUnit->ObjectPlaneQ );
2287 }
2288 else if (pname==GL_EYE_PLANE) {
2289 COPY_4V( params, texUnit->EyePlaneQ );
2290 }
2291 else {
2292 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGenfv(pname)" );
2293 return;
2294 }
2295 break;
2296 default:
2297 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGenfv(coord)" );
2298 return;
2299 }
2300 }
2301
2302
2303
2304 void
2305 _mesa_GetTexGeniv( GLenum coord, GLenum pname, GLint *params )
2306 {
2307 GET_CURRENT_CONTEXT(ctx);
2308 GLuint tUnit = ctx->Texture.CurrentUnit;
2309 struct gl_texture_unit *texUnit = &ctx->Texture.Unit[tUnit];
2310 ASSERT_OUTSIDE_BEGIN_END(ctx);
2311
2312 switch (coord) {
2313 case GL_S:
2314 if (pname==GL_TEXTURE_GEN_MODE) {
2315 params[0] = texUnit->GenModeS;
2316 }
2317 else if (pname==GL_OBJECT_PLANE) {
2318 params[0] = (GLint) texUnit->ObjectPlaneS[0];
2319 params[1] = (GLint) texUnit->ObjectPlaneS[1];
2320 params[2] = (GLint) texUnit->ObjectPlaneS[2];
2321 params[3] = (GLint) texUnit->ObjectPlaneS[3];
2322 }
2323 else if (pname==GL_EYE_PLANE) {
2324 params[0] = (GLint) texUnit->EyePlaneS[0];
2325 params[1] = (GLint) texUnit->EyePlaneS[1];
2326 params[2] = (GLint) texUnit->EyePlaneS[2];
2327 params[3] = (GLint) texUnit->EyePlaneS[3];
2328 }
2329 else {
2330 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGeniv(pname)" );
2331 return;
2332 }
2333 break;
2334 case GL_T:
2335 if (pname==GL_TEXTURE_GEN_MODE) {
2336 params[0] = texUnit->GenModeT;
2337 }
2338 else if (pname==GL_OBJECT_PLANE) {
2339 params[0] = (GLint) texUnit->ObjectPlaneT[0];
2340 params[1] = (GLint) texUnit->ObjectPlaneT[1];
2341 params[2] = (GLint) texUnit->ObjectPlaneT[2];
2342 params[3] = (GLint) texUnit->ObjectPlaneT[3];
2343 }
2344 else if (pname==GL_EYE_PLANE) {
2345 params[0] = (GLint) texUnit->EyePlaneT[0];
2346 params[1] = (GLint) texUnit->EyePlaneT[1];
2347 params[2] = (GLint) texUnit->EyePlaneT[2];
2348 params[3] = (GLint) texUnit->EyePlaneT[3];
2349 }
2350 else {
2351 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGeniv(pname)" );
2352 return;
2353 }
2354 break;
2355 case GL_R:
2356 if (pname==GL_TEXTURE_GEN_MODE) {
2357 params[0] = texUnit->GenModeR;
2358 }
2359 else if (pname==GL_OBJECT_PLANE) {
2360 params[0] = (GLint) texUnit->ObjectPlaneR[0];
2361 params[1] = (GLint) texUnit->ObjectPlaneR[1];
2362 params[2] = (GLint) texUnit->ObjectPlaneR[2];
2363 params[3] = (GLint) texUnit->ObjectPlaneR[3];
2364 }
2365 else if (pname==GL_EYE_PLANE) {
2366 params[0] = (GLint) texUnit->EyePlaneR[0];
2367 params[1] = (GLint) texUnit->EyePlaneR[1];
2368 params[2] = (GLint) texUnit->EyePlaneR[2];
2369 params[3] = (GLint) texUnit->EyePlaneR[3];
2370 }
2371 else {
2372 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGeniv(pname)" );
2373 return;
2374 }
2375 break;
2376 case GL_Q:
2377 if (pname==GL_TEXTURE_GEN_MODE) {
2378 params[0] = texUnit->GenModeQ;
2379 }
2380 else if (pname==GL_OBJECT_PLANE) {
2381 params[0] = (GLint) texUnit->ObjectPlaneQ[0];
2382 params[1] = (GLint) texUnit->ObjectPlaneQ[1];
2383 params[2] = (GLint) texUnit->ObjectPlaneQ[2];
2384 params[3] = (GLint) texUnit->ObjectPlaneQ[3];
2385 }
2386 else if (pname==GL_EYE_PLANE) {
2387 params[0] = (GLint) texUnit->EyePlaneQ[0];
2388 params[1] = (GLint) texUnit->EyePlaneQ[1];
2389 params[2] = (GLint) texUnit->EyePlaneQ[2];
2390 params[3] = (GLint) texUnit->EyePlaneQ[3];
2391 }
2392 else {
2393 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGeniv(pname)" );
2394 return;
2395 }
2396 break;
2397 default:
2398 _mesa_error( ctx, GL_INVALID_ENUM, "glGetTexGeniv(coord)" );
2399 return;
2400 }
2401 }
2402
2403
2404 /* GL_ARB_multitexture */
2405 void
2406 _mesa_ActiveTextureARB( GLenum target )
2407 {
2408 GET_CURRENT_CONTEXT(ctx);
2409 GLuint texUnit = target - GL_TEXTURE0_ARB;
2410 ASSERT_OUTSIDE_BEGIN_END(ctx);
2411
2412 if (MESA_VERBOSE & (VERBOSE_API|VERBOSE_TEXTURE))
2413 _mesa_debug(ctx, "glActiveTexture %s\n",
2414 _mesa_lookup_enum_by_nr(target));
2415
2416 if (texUnit > ctx->Const.MaxTextureUnits) {
2417 _mesa_error(ctx, GL_INVALID_ENUM, "glActiveTextureARB(target)");
2418 return;
2419 }
2420
2421 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
2422 ctx->Texture.CurrentUnit = texUnit;
2423 if (ctx->Driver.ActiveTexture) {
2424 (*ctx->Driver.ActiveTexture)( ctx, (GLuint) texUnit );
2425 }
2426 }
2427
2428
2429 /* GL_ARB_multitexture */
2430 void
2431 _mesa_ClientActiveTextureARB( GLenum target )
2432 {
2433 GET_CURRENT_CONTEXT(ctx);
2434 GLuint texUnit = target - GL_TEXTURE0_ARB;
2435 ASSERT_OUTSIDE_BEGIN_END(ctx);
2436
2437 if (texUnit > ctx->Const.MaxTextureUnits) {
2438 _mesa_error(ctx, GL_INVALID_ENUM, "glClientActiveTextureARB(target)");
2439 return;
2440 }
2441
2442 FLUSH_VERTICES(ctx, _NEW_ARRAY);
2443 ctx->Array.ActiveTexture = texUnit;
2444 }
2445
2446
2447
2448 /**********************************************************************/
2449 /* Pixel Texgen Extensions */
2450 /**********************************************************************/
2451
2452 void
2453 _mesa_PixelTexGenSGIX(GLenum mode)
2454 {
2455 GLenum newRgbSource, newAlphaSource;
2456 GET_CURRENT_CONTEXT(ctx);
2457 ASSERT_OUTSIDE_BEGIN_END(ctx);
2458
2459 switch (mode) {
2460 case GL_NONE:
2461 newRgbSource = GL_PIXEL_GROUP_COLOR_SGIS;
2462 newAlphaSource = GL_PIXEL_GROUP_COLOR_SGIS;
2463 break;
2464 case GL_ALPHA:
2465 newRgbSource = GL_PIXEL_GROUP_COLOR_SGIS;
2466 newAlphaSource = GL_CURRENT_RASTER_COLOR;
2467 break;
2468 case GL_RGB:
2469 newRgbSource = GL_CURRENT_RASTER_COLOR;
2470 newAlphaSource = GL_PIXEL_GROUP_COLOR_SGIS;
2471 break;
2472 case GL_RGBA:
2473 newRgbSource = GL_CURRENT_RASTER_COLOR;
2474 newAlphaSource = GL_CURRENT_RASTER_COLOR;
2475 break;
2476 default:
2477 _mesa_error(ctx, GL_INVALID_ENUM, "glPixelTexGenSGIX(mode)");
2478 return;
2479 }
2480
2481 if (newRgbSource == ctx->Pixel.FragmentRgbSource &&
2482 newAlphaSource == ctx->Pixel.FragmentAlphaSource)
2483 return;
2484
2485 FLUSH_VERTICES(ctx, _NEW_PIXEL);
2486 ctx->Pixel.FragmentRgbSource = newRgbSource;
2487 ctx->Pixel.FragmentAlphaSource = newAlphaSource;
2488 }
2489
2490
2491 void
2492 _mesa_PixelTexGenParameterfSGIS(GLenum target, GLfloat value)
2493 {
2494 _mesa_PixelTexGenParameteriSGIS(target, (GLint) value);
2495 }
2496
2497
2498 void
2499 _mesa_PixelTexGenParameterfvSGIS(GLenum target, const GLfloat *value)
2500 {
2501 _mesa_PixelTexGenParameteriSGIS(target, (GLint) *value);
2502 }
2503
2504
2505 void
2506 _mesa_PixelTexGenParameteriSGIS(GLenum target, GLint value)
2507 {
2508 GET_CURRENT_CONTEXT(ctx);
2509 ASSERT_OUTSIDE_BEGIN_END(ctx);
2510
2511 if (value != GL_CURRENT_RASTER_COLOR && value != GL_PIXEL_GROUP_COLOR_SGIS) {
2512 _mesa_error(ctx, GL_INVALID_ENUM, "glPixelTexGenParameterSGIS(value)");
2513 return;
2514 }
2515
2516 switch (target) {
2517 case GL_PIXEL_FRAGMENT_RGB_SOURCE_SGIS:
2518 if (ctx->Pixel.FragmentRgbSource == (GLenum) value)
2519 return;
2520 FLUSH_VERTICES(ctx, _NEW_PIXEL);
2521 ctx->Pixel.FragmentRgbSource = (GLenum) value;
2522 break;
2523 case GL_PIXEL_FRAGMENT_ALPHA_SOURCE_SGIS:
2524 if (ctx->Pixel.FragmentAlphaSource == (GLenum) value)
2525 return;
2526 FLUSH_VERTICES(ctx, _NEW_PIXEL);
2527 ctx->Pixel.FragmentAlphaSource = (GLenum) value;
2528 break;
2529 default:
2530 _mesa_error(ctx, GL_INVALID_ENUM, "glPixelTexGenParameterSGIS(target)");
2531 return;
2532 }
2533 }
2534
2535
2536 void
2537 _mesa_PixelTexGenParameterivSGIS(GLenum target, const GLint *value)
2538 {
2539 _mesa_PixelTexGenParameteriSGIS(target, *value);
2540 }
2541
2542
2543 void
2544 _mesa_GetPixelTexGenParameterfvSGIS(GLenum target, GLfloat *value)
2545 {
2546 GET_CURRENT_CONTEXT(ctx);
2547 ASSERT_OUTSIDE_BEGIN_END(ctx);
2548
2549 if (target == GL_PIXEL_FRAGMENT_RGB_SOURCE_SGIS) {
2550 *value = (GLfloat) ctx->Pixel.FragmentRgbSource;
2551 }
2552 else if (target == GL_PIXEL_FRAGMENT_ALPHA_SOURCE_SGIS) {
2553 *value = (GLfloat) ctx->Pixel.FragmentAlphaSource;
2554 }
2555 else {
2556 _mesa_error(ctx, GL_INVALID_ENUM, "glGetPixelTexGenParameterfvSGIS(target)");
2557 }
2558 }
2559
2560
2561 void
2562 _mesa_GetPixelTexGenParameterivSGIS(GLenum target, GLint *value)
2563 {
2564 GET_CURRENT_CONTEXT(ctx);
2565 ASSERT_OUTSIDE_BEGIN_END(ctx);
2566
2567 if (target == GL_PIXEL_FRAGMENT_RGB_SOURCE_SGIS) {
2568 *value = (GLint) ctx->Pixel.FragmentRgbSource;
2569 }
2570 else if (target == GL_PIXEL_FRAGMENT_ALPHA_SOURCE_SGIS) {
2571 *value = (GLint) ctx->Pixel.FragmentAlphaSource;
2572 }
2573 else {
2574 _mesa_error(ctx, GL_INVALID_ENUM, "glGetPixelTexGenParameterivSGIS(target)");
2575 }
2576 }