Mesa: allow suppression of debug messages in a debug build
[mesa.git] / src / mesa / main / texparam.c
1 /*
2 * Mesa 3-D graphics library
3 * Version: 7.5
4 *
5 * Copyright (C) 1999-2008 Brian Paul All Rights Reserved.
6 * Copyright (C) 2009 VMware, Inc. All Rights Reserved.
7 *
8 * Permission is hereby granted, free of charge, to any person obtaining a
9 * copy of this software and associated documentation files (the "Software"),
10 * to deal in the Software without restriction, including without limitation
11 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
12 * and/or sell copies of the Software, and to permit persons to whom the
13 * Software is furnished to do so, subject to the following conditions:
14 *
15 * The above copyright notice and this permission notice shall be included
16 * in all copies or substantial portions of the Software.
17 *
18 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
19 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
21 * BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
22 * AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
23 * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
24 */
25
26 /**
27 * \file texparam.c
28 *
29 * glTexParameter-related functions
30 */
31
32
33 #include "main/glheader.h"
34 #include "main/context.h"
35 #include "main/enums.h"
36 #include "main/colormac.h"
37 #include "main/macros.h"
38 #include "main/texcompress.h"
39 #include "main/texparam.h"
40 #include "main/teximage.h"
41 #include "shader/prog_instruction.h"
42
43
44 /**
45 * Check if a coordinate wrap mode is supported for the texture target.
46 * \return GL_TRUE if legal, GL_FALSE otherwise
47 */
48 static GLboolean
49 validate_texture_wrap_mode(GLcontext * ctx, GLenum target, GLenum wrap)
50 {
51 const struct gl_extensions * const e = & ctx->Extensions;
52
53 if (wrap == GL_CLAMP || wrap == GL_CLAMP_TO_EDGE ||
54 (wrap == GL_CLAMP_TO_BORDER && e->ARB_texture_border_clamp)) {
55 /* any texture target */
56 return GL_TRUE;
57 }
58 else if (target != GL_TEXTURE_RECTANGLE_NV &&
59 (wrap == GL_REPEAT ||
60 (wrap == GL_MIRRORED_REPEAT &&
61 e->ARB_texture_mirrored_repeat) ||
62 (wrap == GL_MIRROR_CLAMP_EXT &&
63 (e->ATI_texture_mirror_once || e->EXT_texture_mirror_clamp)) ||
64 (wrap == GL_MIRROR_CLAMP_TO_EDGE_EXT &&
65 (e->ATI_texture_mirror_once || e->EXT_texture_mirror_clamp)) ||
66 (wrap == GL_MIRROR_CLAMP_TO_BORDER_EXT &&
67 (e->EXT_texture_mirror_clamp)))) {
68 /* non-rectangle texture */
69 return GL_TRUE;
70 }
71
72 _mesa_error( ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
73 return GL_FALSE;
74 }
75
76
77 /**
78 * Get current texture object for given target.
79 * Return NULL if any error.
80 */
81 static struct gl_texture_object *
82 get_texobj(GLcontext *ctx, GLenum target)
83 {
84 struct gl_texture_unit *texUnit;
85
86 if (ctx->Texture.CurrentUnit >= ctx->Const.MaxTextureImageUnits) {
87 _mesa_error(ctx, GL_INVALID_OPERATION, "glTexParameter(current unit)");
88 return NULL;
89 }
90
91 texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
92
93 switch (target) {
94 case GL_TEXTURE_1D:
95 return texUnit->CurrentTex[TEXTURE_1D_INDEX];
96 case GL_TEXTURE_2D:
97 return texUnit->CurrentTex[TEXTURE_2D_INDEX];
98 case GL_TEXTURE_3D:
99 return texUnit->CurrentTex[TEXTURE_3D_INDEX];
100 case GL_TEXTURE_CUBE_MAP:
101 if (ctx->Extensions.ARB_texture_cube_map) {
102 return texUnit->CurrentTex[TEXTURE_CUBE_INDEX];
103 }
104 break;
105 case GL_TEXTURE_RECTANGLE_NV:
106 if (ctx->Extensions.NV_texture_rectangle) {
107 return texUnit->CurrentTex[TEXTURE_RECT_INDEX];
108 }
109 break;
110 case GL_TEXTURE_1D_ARRAY_EXT:
111 if (ctx->Extensions.MESA_texture_array) {
112 return texUnit->CurrentTex[TEXTURE_1D_ARRAY_INDEX];
113 }
114 break;
115 case GL_TEXTURE_2D_ARRAY_EXT:
116 if (ctx->Extensions.MESA_texture_array) {
117 return texUnit->CurrentTex[TEXTURE_2D_ARRAY_INDEX];
118 }
119 break;
120 default:
121 ;
122 }
123
124 _mesa_error(ctx, GL_INVALID_ENUM, "glTexParameter(target)");
125 return NULL;
126 }
127
128
129 /**
130 * Convert GL_RED/GREEN/BLUE/ALPHA/ZERO/ONE to SWIZZLE_X/Y/Z/W/ZERO/ONE.
131 * \return -1 if error.
132 */
133 static GLint
134 comp_to_swizzle(GLenum comp)
135 {
136 switch (comp) {
137 case GL_RED:
138 return SWIZZLE_X;
139 case GL_GREEN:
140 return SWIZZLE_Y;
141 case GL_BLUE:
142 return SWIZZLE_Z;
143 case GL_ALPHA:
144 return SWIZZLE_W;
145 case GL_ZERO:
146 return SWIZZLE_ZERO;
147 case GL_ONE:
148 return SWIZZLE_ONE;
149 default:
150 return -1;
151 }
152 }
153
154
155 static void
156 set_swizzle_component(GLuint *swizzle, GLuint comp, GLuint swz)
157 {
158 ASSERT(comp < 4);
159 ASSERT(swz <= SWIZZLE_NIL);
160 {
161 GLuint mask = 0x7 << (3 * comp);
162 GLuint s = (*swizzle & ~mask) | (swz << (3 * comp));
163 *swizzle = s;
164 }
165 }
166
167
168 /**
169 * This is called just prior to changing any texture object state.
170 * Any pending rendering will be flushed out, we'll set the _NEW_TEXTURE
171 * state flag and then mark the texture object as 'incomplete' so that any
172 * per-texture derived state gets recomputed.
173 */
174 static INLINE void
175 flush(GLcontext *ctx, struct gl_texture_object *texObj)
176 {
177 FLUSH_VERTICES(ctx, _NEW_TEXTURE);
178 texObj->_Complete = GL_FALSE;
179 }
180
181
182 /**
183 * Set an integer-valued texture parameter
184 * \return GL_TRUE if legal AND the value changed, GL_FALSE otherwise
185 */
186 static GLboolean
187 set_tex_parameteri(GLcontext *ctx,
188 struct gl_texture_object *texObj,
189 GLenum pname, const GLint *params)
190 {
191 switch (pname) {
192 case GL_TEXTURE_MIN_FILTER:
193 if (texObj->MinFilter == params[0])
194 return GL_FALSE;
195 switch (params[0]) {
196 case GL_NEAREST:
197 case GL_LINEAR:
198 flush(ctx, texObj);
199 texObj->MinFilter = params[0];
200 return GL_TRUE;
201 case GL_NEAREST_MIPMAP_NEAREST:
202 case GL_LINEAR_MIPMAP_NEAREST:
203 case GL_NEAREST_MIPMAP_LINEAR:
204 case GL_LINEAR_MIPMAP_LINEAR:
205 if (texObj->Target != GL_TEXTURE_RECTANGLE_NV) {
206 flush(ctx, texObj);
207 texObj->MinFilter = params[0];
208 return GL_TRUE;
209 }
210 /* fall-through */
211 default:
212 _mesa_error( ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
213 }
214 return GL_FALSE;
215
216 case GL_TEXTURE_MAG_FILTER:
217 if (texObj->MagFilter == params[0])
218 return GL_FALSE;
219 switch (params[0]) {
220 case GL_NEAREST:
221 case GL_LINEAR:
222 flush(ctx, texObj);
223 texObj->MagFilter = params[0];
224 return GL_TRUE;
225 default:
226 _mesa_error( ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
227 }
228 return GL_FALSE;
229
230 case GL_TEXTURE_WRAP_S:
231 if (texObj->WrapS == params[0])
232 return GL_FALSE;
233 if (validate_texture_wrap_mode(ctx, texObj->Target, params[0])) {
234 flush(ctx, texObj);
235 texObj->WrapS = params[0];
236 return GL_TRUE;
237 }
238 return GL_FALSE;
239
240 case GL_TEXTURE_WRAP_T:
241 if (texObj->WrapT == params[0])
242 return GL_FALSE;
243 if (validate_texture_wrap_mode(ctx, texObj->Target, params[0])) {
244 flush(ctx, texObj);
245 texObj->WrapT = params[0];
246 return GL_TRUE;
247 }
248 return GL_FALSE;
249
250 case GL_TEXTURE_WRAP_R:
251 if (texObj->WrapR == params[0])
252 return GL_FALSE;
253 if (validate_texture_wrap_mode(ctx, texObj->Target, params[0])) {
254 flush(ctx, texObj);
255 texObj->WrapR = params[0];
256 return GL_TRUE;
257 }
258 return GL_FALSE;
259
260 case GL_TEXTURE_BASE_LEVEL:
261 if (texObj->BaseLevel == params[0])
262 return GL_FALSE;
263 if (params[0] < 0 ||
264 (texObj->Target == GL_TEXTURE_RECTANGLE_ARB && params[0] != 0)) {
265 _mesa_error(ctx, GL_INVALID_VALUE, "glTexParameter(param)");
266 return GL_FALSE;
267 }
268 flush(ctx, texObj);
269 texObj->BaseLevel = params[0];
270 return GL_TRUE;
271
272 case GL_TEXTURE_MAX_LEVEL:
273 if (texObj->MaxLevel == params[0])
274 return GL_FALSE;
275 if (params[0] < 0 || texObj->Target == GL_TEXTURE_RECTANGLE_ARB) {
276 _mesa_error(ctx, GL_INVALID_OPERATION, "glTexParameter(param)");
277 return GL_FALSE;
278 }
279 flush(ctx, texObj);
280 texObj->MaxLevel = params[0];
281 return GL_TRUE;
282
283 case GL_GENERATE_MIPMAP_SGIS:
284 if (ctx->Extensions.SGIS_generate_mipmap) {
285 if (texObj->GenerateMipmap != params[0]) {
286 flush(ctx, texObj);
287 texObj->GenerateMipmap = params[0] ? GL_TRUE : GL_FALSE;
288 return GL_TRUE;
289 }
290 return GL_FALSE;
291 }
292 else {
293 _mesa_error(ctx, GL_INVALID_ENUM,
294 "glTexParameter(pname=GL_GENERATE_MIPMAP_SGIS)");
295 }
296 return GL_FALSE;
297
298 case GL_TEXTURE_COMPARE_MODE_ARB:
299 if (ctx->Extensions.ARB_shadow &&
300 (params[0] == GL_NONE ||
301 params[0] == GL_COMPARE_R_TO_TEXTURE_ARB)) {
302 if (texObj->CompareMode != params[0]) {
303 flush(ctx, texObj);
304 texObj->CompareMode = params[0];
305 return GL_TRUE;
306 }
307 return GL_FALSE;
308 }
309 else {
310 _mesa_error(ctx, GL_INVALID_ENUM,
311 "glTexParameter(GL_TEXTURE_COMPARE_MODE_ARB)");
312 }
313 return GL_FALSE;
314
315 case GL_TEXTURE_COMPARE_FUNC_ARB:
316 if (ctx->Extensions.ARB_shadow) {
317 if (texObj->CompareFunc == params[0])
318 return GL_FALSE;
319 switch (params[0]) {
320 case GL_LEQUAL:
321 case GL_GEQUAL:
322 flush(ctx, texObj);
323 texObj->CompareFunc = params[0];
324 return GL_TRUE;
325 case GL_EQUAL:
326 case GL_NOTEQUAL:
327 case GL_LESS:
328 case GL_GREATER:
329 case GL_ALWAYS:
330 case GL_NEVER:
331 if (ctx->Extensions.EXT_shadow_funcs) {
332 flush(ctx, texObj);
333 texObj->CompareFunc = params[0];
334 return GL_TRUE;
335 }
336 /* fall-through */
337 default:
338 _mesa_error(ctx, GL_INVALID_ENUM,
339 "glTexParameter(GL_TEXTURE_COMPARE_FUNC_ARB)");
340 }
341 }
342 else {
343 _mesa_error(ctx, GL_INVALID_ENUM, "glTexParameter(param)");
344 }
345 return GL_FALSE;
346
347 case GL_DEPTH_TEXTURE_MODE_ARB:
348 if (ctx->Extensions.ARB_depth_texture &&
349 (params[0] == GL_LUMINANCE ||
350 params[0] == GL_INTENSITY ||
351 params[0] == GL_ALPHA)) {
352 if (texObj->DepthMode != params[0]) {
353 flush(ctx, texObj);
354 texObj->DepthMode = params[0];
355 return GL_TRUE;
356 }
357 }
358 else {
359 _mesa_error(ctx, GL_INVALID_ENUM,
360 "glTexParameter(GL_DEPTH_TEXTURE_MODE_ARB)");
361 }
362 return GL_FALSE;
363
364 #ifdef FEATURE_OES_draw_texture
365 case GL_TEXTURE_CROP_RECT_OES:
366 texObj->CropRect[0] = params[0];
367 texObj->CropRect[1] = params[1];
368 texObj->CropRect[2] = params[2];
369 texObj->CropRect[3] = params[3];
370 return GL_TRUE;
371 #endif
372
373 case GL_TEXTURE_SWIZZLE_R_EXT:
374 case GL_TEXTURE_SWIZZLE_G_EXT:
375 case GL_TEXTURE_SWIZZLE_B_EXT:
376 case GL_TEXTURE_SWIZZLE_A_EXT:
377 if (ctx->Extensions.EXT_texture_swizzle) {
378 const GLuint comp = pname - GL_TEXTURE_SWIZZLE_R_EXT;
379 const GLint swz = comp_to_swizzle(params[0]);
380 if (swz < 0) {
381 _mesa_error(ctx, GL_INVALID_OPERATION,
382 "glTexParameter(swizzle 0x%x)", params[0]);
383 return GL_FALSE;
384 }
385 ASSERT(comp < 4);
386 if (swz >= 0) {
387 flush(ctx, texObj);
388 texObj->Swizzle[comp] = params[0];
389 set_swizzle_component(&texObj->_Swizzle, comp, swz);
390 return GL_TRUE;
391 }
392 }
393 _mesa_error(ctx, GL_INVALID_ENUM, "glTexParameter(pname=0x%x)", pname);
394 return GL_FALSE;
395
396 case GL_TEXTURE_SWIZZLE_RGBA_EXT:
397 if (ctx->Extensions.EXT_texture_swizzle) {
398 GLuint comp;
399 flush(ctx, texObj);
400 for (comp = 0; comp < 4; comp++) {
401 const GLint swz = comp_to_swizzle(params[comp]);
402 if (swz >= 0) {
403 texObj->Swizzle[comp] = params[comp];
404 set_swizzle_component(&texObj->_Swizzle, comp, swz);
405 }
406 else {
407 _mesa_error(ctx, GL_INVALID_OPERATION,
408 "glTexParameter(swizzle 0x%x)", params[comp]);
409 return GL_FALSE;
410 }
411 }
412 return GL_TRUE;
413 }
414 _mesa_error(ctx, GL_INVALID_ENUM, "glTexParameter(pname=0x%x)", pname);
415 return GL_FALSE;
416
417 default:
418 _mesa_error(ctx, GL_INVALID_ENUM, "glTexParameter(pname=0x%x)", pname);
419 }
420 return GL_FALSE;
421 }
422
423
424 /**
425 * Set a float-valued texture parameter
426 * \return GL_TRUE if legal AND the value changed, GL_FALSE otherwise
427 */
428 static GLboolean
429 set_tex_parameterf(GLcontext *ctx,
430 struct gl_texture_object *texObj,
431 GLenum pname, const GLfloat *params)
432 {
433 switch (pname) {
434 case GL_TEXTURE_MIN_LOD:
435 if (texObj->MinLod == params[0])
436 return GL_FALSE;
437 flush(ctx, texObj);
438 texObj->MinLod = params[0];
439 return GL_TRUE;
440
441 case GL_TEXTURE_MAX_LOD:
442 if (texObj->MaxLod == params[0])
443 return GL_FALSE;
444 flush(ctx, texObj);
445 texObj->MaxLod = params[0];
446 return GL_TRUE;
447
448 case GL_TEXTURE_PRIORITY:
449 flush(ctx, texObj);
450 texObj->Priority = CLAMP(params[0], 0.0F, 1.0F);
451 return GL_TRUE;
452
453 case GL_TEXTURE_MAX_ANISOTROPY_EXT:
454 if (ctx->Extensions.EXT_texture_filter_anisotropic) {
455 if (texObj->MaxAnisotropy == params[0])
456 return GL_FALSE;
457 if (params[0] < 1.0) {
458 _mesa_error(ctx, GL_INVALID_VALUE, "glTexParameter(param)" );
459 return GL_FALSE;
460 }
461 flush(ctx, texObj);
462 /* clamp to max, that's what NVIDIA does */
463 texObj->MaxAnisotropy = MIN2(params[0],
464 ctx->Const.MaxTextureMaxAnisotropy);
465 return GL_TRUE;
466 }
467 else {
468 _mesa_error(ctx, GL_INVALID_ENUM,
469 "glTexParameter(pname=GL_TEXTURE_MAX_ANISOTROPY_EXT)");
470 }
471 return GL_FALSE;
472
473 case GL_TEXTURE_COMPARE_FAIL_VALUE_ARB:
474 if (ctx->Extensions.ARB_shadow_ambient) {
475 if (texObj->CompareFailValue != params[0]) {
476 flush(ctx, texObj);
477 texObj->CompareFailValue = CLAMP(params[0], 0.0F, 1.0F);
478 return GL_TRUE;
479 }
480 }
481 else {
482 _mesa_error(ctx, GL_INVALID_ENUM,
483 "glTexParameter(pname=GL_TEXTURE_COMPARE_FAIL_VALUE_ARB)");
484 }
485 return GL_FALSE;
486
487 case GL_TEXTURE_LOD_BIAS:
488 /* NOTE: this is really part of OpenGL 1.4, not EXT_texture_lod_bias */
489 if (ctx->Extensions.EXT_texture_lod_bias) {
490 if (texObj->LodBias != params[0]) {
491 flush(ctx, texObj);
492 texObj->LodBias = params[0];
493 return GL_TRUE;
494 }
495 return GL_FALSE;
496 }
497 break;
498
499 case GL_TEXTURE_BORDER_COLOR:
500 flush(ctx, texObj);
501 texObj->BorderColor[RCOMP] = params[0];
502 texObj->BorderColor[GCOMP] = params[1];
503 texObj->BorderColor[BCOMP] = params[2];
504 texObj->BorderColor[ACOMP] = params[3];
505 return GL_TRUE;
506
507 default:
508 _mesa_error(ctx, GL_INVALID_ENUM, "glTexParameter(pname=0x%x)", pname);
509 }
510 return GL_FALSE;
511 }
512
513
514 void GLAPIENTRY
515 _mesa_TexParameterf(GLenum target, GLenum pname, GLfloat param)
516 {
517 GLboolean need_update;
518 struct gl_texture_object *texObj;
519 GET_CURRENT_CONTEXT(ctx);
520 ASSERT_OUTSIDE_BEGIN_END(ctx);
521
522 texObj = get_texobj(ctx, target);
523 if (!texObj)
524 return;
525
526 switch (pname) {
527 case GL_TEXTURE_MIN_FILTER:
528 case GL_TEXTURE_MAG_FILTER:
529 case GL_TEXTURE_WRAP_S:
530 case GL_TEXTURE_WRAP_T:
531 case GL_TEXTURE_WRAP_R:
532 case GL_TEXTURE_BASE_LEVEL:
533 case GL_TEXTURE_MAX_LEVEL:
534 case GL_GENERATE_MIPMAP_SGIS:
535 case GL_TEXTURE_COMPARE_MODE_ARB:
536 case GL_TEXTURE_COMPARE_FUNC_ARB:
537 case GL_DEPTH_TEXTURE_MODE_ARB:
538 {
539 /* convert float param to int */
540 GLint p = (GLint) param;
541 need_update = set_tex_parameteri(ctx, texObj, pname, &p);
542 }
543 break;
544 default:
545 /* this will generate an error if pname is illegal */
546 need_update = set_tex_parameterf(ctx, texObj, pname, &param);
547 }
548
549 if (ctx->Driver.TexParameter && need_update) {
550 ctx->Driver.TexParameter(ctx, target, texObj, pname, &param);
551 }
552 }
553
554
555 void GLAPIENTRY
556 _mesa_TexParameterfv(GLenum target, GLenum pname, const GLfloat *params)
557 {
558 GLboolean need_update;
559 struct gl_texture_object *texObj;
560 GET_CURRENT_CONTEXT(ctx);
561 ASSERT_OUTSIDE_BEGIN_END(ctx);
562
563 texObj = get_texobj(ctx, target);
564 if (!texObj)
565 return;
566
567 switch (pname) {
568 case GL_TEXTURE_MIN_FILTER:
569 case GL_TEXTURE_MAG_FILTER:
570 case GL_TEXTURE_WRAP_S:
571 case GL_TEXTURE_WRAP_T:
572 case GL_TEXTURE_WRAP_R:
573 case GL_TEXTURE_BASE_LEVEL:
574 case GL_TEXTURE_MAX_LEVEL:
575 case GL_GENERATE_MIPMAP_SGIS:
576 case GL_TEXTURE_COMPARE_MODE_ARB:
577 case GL_TEXTURE_COMPARE_FUNC_ARB:
578 case GL_DEPTH_TEXTURE_MODE_ARB:
579 {
580 /* convert float param to int */
581 GLint p = (GLint) params[0];
582 need_update = set_tex_parameteri(ctx, texObj, pname, &p);
583 }
584 break;
585
586 #ifdef FEATURE_OES_draw_texture
587 case GL_TEXTURE_CROP_RECT_OES:
588 {
589 /* convert float params to int */
590 GLint iparams[4];
591 iparams[0] = (GLint) params[0];
592 iparams[1] = (GLint) params[1];
593 iparams[2] = (GLint) params[2];
594 iparams[3] = (GLint) params[3];
595 need_update = set_tex_parameteri(ctx, target, iparams);
596 }
597 break;
598 #endif
599
600 default:
601 /* this will generate an error if pname is illegal */
602 need_update = set_tex_parameterf(ctx, texObj, pname, params);
603 }
604
605 if (ctx->Driver.TexParameter && need_update) {
606 ctx->Driver.TexParameter(ctx, target, texObj, pname, params);
607 }
608 }
609
610
611 void GLAPIENTRY
612 _mesa_TexParameteri(GLenum target, GLenum pname, GLint param)
613 {
614 GLboolean need_update;
615 struct gl_texture_object *texObj;
616 GET_CURRENT_CONTEXT(ctx);
617 ASSERT_OUTSIDE_BEGIN_END(ctx);
618
619 texObj = get_texobj(ctx, target);
620 if (!texObj)
621 return;
622
623 switch (pname) {
624 case GL_TEXTURE_MIN_LOD:
625 case GL_TEXTURE_MAX_LOD:
626 case GL_TEXTURE_PRIORITY:
627 case GL_TEXTURE_MAX_ANISOTROPY_EXT:
628 case GL_TEXTURE_LOD_BIAS:
629 case GL_TEXTURE_COMPARE_FAIL_VALUE_ARB:
630 {
631 GLfloat fparam = (GLfloat) param;
632 /* convert int param to float */
633 need_update = set_tex_parameterf(ctx, texObj, pname, &fparam);
634 }
635 break;
636 default:
637 /* this will generate an error if pname is illegal */
638 need_update = set_tex_parameteri(ctx, texObj, pname, &param);
639 }
640
641 if (ctx->Driver.TexParameter && need_update) {
642 GLfloat fparam = (GLfloat) param;
643 ctx->Driver.TexParameter(ctx, target, texObj, pname, &fparam);
644 }
645 }
646
647
648 void GLAPIENTRY
649 _mesa_TexParameteriv(GLenum target, GLenum pname, const GLint *params)
650 {
651 GLboolean need_update;
652 struct gl_texture_object *texObj;
653 GET_CURRENT_CONTEXT(ctx);
654 ASSERT_OUTSIDE_BEGIN_END(ctx);
655
656 texObj = get_texobj(ctx, target);
657 if (!texObj)
658 return;
659
660 switch (pname) {
661 case GL_TEXTURE_BORDER_COLOR:
662 {
663 /* convert int params to float */
664 GLfloat fparams[4];
665 fparams[0] = INT_TO_FLOAT(params[0]);
666 fparams[1] = INT_TO_FLOAT(params[1]);
667 fparams[2] = INT_TO_FLOAT(params[2]);
668 fparams[3] = INT_TO_FLOAT(params[3]);
669 need_update = set_tex_parameterf(ctx, texObj, pname, fparams);
670 }
671 break;
672 case GL_TEXTURE_MIN_LOD:
673 case GL_TEXTURE_MAX_LOD:
674 case GL_TEXTURE_PRIORITY:
675 case GL_TEXTURE_MAX_ANISOTROPY_EXT:
676 case GL_TEXTURE_LOD_BIAS:
677 case GL_TEXTURE_COMPARE_FAIL_VALUE_ARB:
678 {
679 /* convert int param to float */
680 GLfloat fparam = (GLfloat) params[0];
681 need_update = set_tex_parameterf(ctx, texObj, pname, &fparam);
682 }
683 break;
684 default:
685 /* this will generate an error if pname is illegal */
686 need_update = set_tex_parameteri(ctx, texObj, pname, params);
687 }
688
689 if (ctx->Driver.TexParameter && need_update) {
690 GLfloat fparams[4];
691 fparams[0] = INT_TO_FLOAT(params[0]);
692 if (pname == GL_TEXTURE_BORDER_COLOR ||
693 pname == GL_TEXTURE_CROP_RECT_OES) {
694 fparams[1] = INT_TO_FLOAT(params[1]);
695 fparams[2] = INT_TO_FLOAT(params[2]);
696 fparams[3] = INT_TO_FLOAT(params[3]);
697 }
698 ctx->Driver.TexParameter(ctx, target, texObj, pname, fparams);
699 }
700 }
701
702
703 void GLAPIENTRY
704 _mesa_GetTexLevelParameterfv( GLenum target, GLint level,
705 GLenum pname, GLfloat *params )
706 {
707 GLint iparam;
708 _mesa_GetTexLevelParameteriv( target, level, pname, &iparam );
709 *params = (GLfloat) iparam;
710 }
711
712
713 static GLuint
714 tex_image_dimensions(GLcontext *ctx, GLenum target)
715 {
716 switch (target) {
717 case GL_TEXTURE_1D:
718 case GL_PROXY_TEXTURE_1D:
719 return 1;
720 case GL_TEXTURE_2D:
721 case GL_PROXY_TEXTURE_2D:
722 return 2;
723 case GL_TEXTURE_3D:
724 case GL_PROXY_TEXTURE_3D:
725 return 3;
726 case GL_TEXTURE_CUBE_MAP:
727 case GL_PROXY_TEXTURE_CUBE_MAP:
728 case GL_TEXTURE_CUBE_MAP_POSITIVE_X:
729 case GL_TEXTURE_CUBE_MAP_NEGATIVE_X:
730 case GL_TEXTURE_CUBE_MAP_POSITIVE_Y:
731 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Y:
732 case GL_TEXTURE_CUBE_MAP_POSITIVE_Z:
733 case GL_TEXTURE_CUBE_MAP_NEGATIVE_Z:
734 return ctx->Extensions.ARB_texture_cube_map ? 2 : 0;
735 case GL_TEXTURE_RECTANGLE_NV:
736 case GL_PROXY_TEXTURE_RECTANGLE_NV:
737 return ctx->Extensions.NV_texture_rectangle ? 2 : 0;
738 case GL_TEXTURE_1D_ARRAY_EXT:
739 case GL_PROXY_TEXTURE_1D_ARRAY_EXT:
740 return ctx->Extensions.MESA_texture_array ? 2 : 0;
741 case GL_TEXTURE_2D_ARRAY_EXT:
742 case GL_PROXY_TEXTURE_2D_ARRAY_EXT:
743 return ctx->Extensions.MESA_texture_array ? 3 : 0;
744 default:
745 _mesa_problem(ctx, "bad target in _mesa_tex_target_dimensions()");
746 return 0;
747 }
748 }
749
750
751 void GLAPIENTRY
752 _mesa_GetTexLevelParameteriv( GLenum target, GLint level,
753 GLenum pname, GLint *params )
754 {
755 const struct gl_texture_unit *texUnit;
756 struct gl_texture_object *texObj;
757 const struct gl_texture_image *img = NULL;
758 GLuint dimensions;
759 GLboolean isProxy;
760 GLint maxLevels;
761 GET_CURRENT_CONTEXT(ctx);
762 ASSERT_OUTSIDE_BEGIN_END(ctx);
763
764 if (ctx->Texture.CurrentUnit >= ctx->Const.MaxTextureImageUnits) {
765 _mesa_error(ctx, GL_INVALID_OPERATION,
766 "glGetTexLevelParameteriv(current unit)");
767 return;
768 }
769
770 texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
771
772 /* this will catch bad target values */
773 dimensions = tex_image_dimensions(ctx, target); /* 1, 2 or 3 */
774 if (dimensions == 0) {
775 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexLevelParameter[if]v(target)");
776 return;
777 }
778
779 maxLevels = _mesa_max_texture_levels(ctx, target);
780 if (maxLevels == 0) {
781 /* should not happen since <target> was just checked above */
782 _mesa_problem(ctx, "maxLevels=0 in _mesa_GetTexLevelParameter");
783 return;
784 }
785
786 if (level < 0 || level >= maxLevels) {
787 _mesa_error( ctx, GL_INVALID_VALUE, "glGetTexLevelParameter[if]v" );
788 return;
789 }
790
791 texObj = _mesa_select_tex_object(ctx, texUnit, target);
792 _mesa_lock_texture(ctx, texObj);
793
794 img = _mesa_select_tex_image(ctx, texObj, target, level);
795 if (!img || !img->TexFormat) {
796 /* undefined texture image */
797 if (pname == GL_TEXTURE_COMPONENTS)
798 *params = 1;
799 else
800 *params = 0;
801 goto out;
802 }
803
804 isProxy = _mesa_is_proxy_texture(target);
805
806 switch (pname) {
807 case GL_TEXTURE_WIDTH:
808 *params = img->Width;
809 break;
810 case GL_TEXTURE_HEIGHT:
811 *params = img->Height;
812 break;
813 case GL_TEXTURE_DEPTH:
814 *params = img->Depth;
815 break;
816 case GL_TEXTURE_INTERNAL_FORMAT:
817 *params = img->InternalFormat;
818 break;
819 case GL_TEXTURE_BORDER:
820 *params = img->Border;
821 break;
822 case GL_TEXTURE_RED_SIZE:
823 if (img->_BaseFormat == GL_RGB || img->_BaseFormat == GL_RGBA)
824 *params = img->TexFormat->RedBits;
825 else
826 *params = 0;
827 break;
828 case GL_TEXTURE_GREEN_SIZE:
829 if (img->_BaseFormat == GL_RGB || img->_BaseFormat == GL_RGBA)
830 *params = img->TexFormat->GreenBits;
831 else
832 *params = 0;
833 break;
834 case GL_TEXTURE_BLUE_SIZE:
835 if (img->_BaseFormat == GL_RGB || img->_BaseFormat == GL_RGBA)
836 *params = img->TexFormat->BlueBits;
837 else
838 *params = 0;
839 break;
840 case GL_TEXTURE_ALPHA_SIZE:
841 if (img->_BaseFormat == GL_ALPHA ||
842 img->_BaseFormat == GL_LUMINANCE_ALPHA ||
843 img->_BaseFormat == GL_RGBA)
844 *params = img->TexFormat->AlphaBits;
845 else
846 *params = 0;
847 break;
848 case GL_TEXTURE_INTENSITY_SIZE:
849 if (img->_BaseFormat != GL_INTENSITY)
850 *params = 0;
851 else if (img->TexFormat->IntensityBits > 0)
852 *params = img->TexFormat->IntensityBits;
853 else /* intensity probably stored as rgb texture */
854 *params = MIN2(img->TexFormat->RedBits, img->TexFormat->GreenBits);
855 break;
856 case GL_TEXTURE_LUMINANCE_SIZE:
857 if (img->_BaseFormat != GL_LUMINANCE &&
858 img->_BaseFormat != GL_LUMINANCE_ALPHA)
859 *params = 0;
860 else if (img->TexFormat->LuminanceBits > 0)
861 *params = img->TexFormat->LuminanceBits;
862 else /* luminance probably stored as rgb texture */
863 *params = MIN2(img->TexFormat->RedBits, img->TexFormat->GreenBits);
864 break;
865 case GL_TEXTURE_INDEX_SIZE_EXT:
866 if (img->_BaseFormat == GL_COLOR_INDEX)
867 *params = img->TexFormat->IndexBits;
868 else
869 *params = 0;
870 break;
871 case GL_TEXTURE_DEPTH_SIZE_ARB:
872 if (ctx->Extensions.ARB_depth_texture)
873 *params = img->TexFormat->DepthBits;
874 else
875 _mesa_error(ctx, GL_INVALID_ENUM,
876 "glGetTexLevelParameter[if]v(pname)");
877 break;
878 case GL_TEXTURE_STENCIL_SIZE_EXT:
879 if (ctx->Extensions.EXT_packed_depth_stencil) {
880 *params = img->TexFormat->StencilBits;
881 }
882 else {
883 _mesa_error(ctx, GL_INVALID_ENUM,
884 "glGetTexLevelParameter[if]v(pname)");
885 }
886 break;
887
888 /* GL_ARB_texture_compression */
889 case GL_TEXTURE_COMPRESSED_IMAGE_SIZE:
890 if (img->IsCompressed && !isProxy) {
891 /* Don't use ctx->Driver.CompressedTextureSize() since that
892 * may returned a padded hardware size.
893 */
894 *params = _mesa_compressed_texture_size(ctx, img->Width,
895 img->Height, img->Depth,
896 img->TexFormat->MesaFormat);
897 }
898 else {
899 _mesa_error(ctx, GL_INVALID_OPERATION,
900 "glGetTexLevelParameter[if]v(pname)");
901 }
902 break;
903 case GL_TEXTURE_COMPRESSED:
904 *params = (GLint) img->IsCompressed;
905 break;
906
907 /* GL_ARB_texture_float */
908 case GL_TEXTURE_RED_TYPE_ARB:
909 if (ctx->Extensions.ARB_texture_float) {
910 *params = img->TexFormat->RedBits ? img->TexFormat->DataType : GL_NONE;
911 }
912 else {
913 _mesa_error(ctx, GL_INVALID_ENUM,
914 "glGetTexLevelParameter[if]v(pname)");
915 }
916 break;
917 case GL_TEXTURE_GREEN_TYPE_ARB:
918 if (ctx->Extensions.ARB_texture_float) {
919 *params = img->TexFormat->GreenBits ? img->TexFormat->DataType : GL_NONE;
920 }
921 else {
922 _mesa_error(ctx, GL_INVALID_ENUM,
923 "glGetTexLevelParameter[if]v(pname)");
924 }
925 break;
926 case GL_TEXTURE_BLUE_TYPE_ARB:
927 if (ctx->Extensions.ARB_texture_float) {
928 *params = img->TexFormat->BlueBits ? img->TexFormat->DataType : GL_NONE;
929 }
930 else {
931 _mesa_error(ctx, GL_INVALID_ENUM,
932 "glGetTexLevelParameter[if]v(pname)");
933 }
934 break;
935 case GL_TEXTURE_ALPHA_TYPE_ARB:
936 if (ctx->Extensions.ARB_texture_float) {
937 *params = img->TexFormat->AlphaBits ? img->TexFormat->DataType : GL_NONE;
938 }
939 else {
940 _mesa_error(ctx, GL_INVALID_ENUM,
941 "glGetTexLevelParameter[if]v(pname)");
942 }
943 break;
944 case GL_TEXTURE_LUMINANCE_TYPE_ARB:
945 if (ctx->Extensions.ARB_texture_float) {
946 *params = img->TexFormat->LuminanceBits ? img->TexFormat->DataType : GL_NONE;
947 }
948 else {
949 _mesa_error(ctx, GL_INVALID_ENUM,
950 "glGetTexLevelParameter[if]v(pname)");
951 }
952 break;
953 case GL_TEXTURE_INTENSITY_TYPE_ARB:
954 if (ctx->Extensions.ARB_texture_float) {
955 *params = img->TexFormat->IntensityBits ? img->TexFormat->DataType : GL_NONE;
956 }
957 else {
958 _mesa_error(ctx, GL_INVALID_ENUM,
959 "glGetTexLevelParameter[if]v(pname)");
960 }
961 break;
962 case GL_TEXTURE_DEPTH_TYPE_ARB:
963 if (ctx->Extensions.ARB_texture_float) {
964 *params = img->TexFormat->DepthBits ? img->TexFormat->DataType : GL_NONE;
965 }
966 else {
967 _mesa_error(ctx, GL_INVALID_ENUM,
968 "glGetTexLevelParameter[if]v(pname)");
969 }
970 break;
971
972 default:
973 _mesa_error(ctx, GL_INVALID_ENUM,
974 "glGetTexLevelParameter[if]v(pname)");
975 }
976
977 out:
978 _mesa_unlock_texture(ctx, texObj);
979 }
980
981
982
983 void GLAPIENTRY
984 _mesa_GetTexParameterfv( GLenum target, GLenum pname, GLfloat *params )
985 {
986 struct gl_texture_unit *texUnit;
987 struct gl_texture_object *obj;
988 GLboolean error = GL_FALSE;
989 GET_CURRENT_CONTEXT(ctx);
990 ASSERT_OUTSIDE_BEGIN_END(ctx);
991
992 if (ctx->Texture.CurrentUnit >= ctx->Const.MaxTextureImageUnits) {
993 _mesa_error(ctx, GL_INVALID_OPERATION,
994 "glGetTexParameterfv(current unit)");
995 return;
996 }
997
998 texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
999
1000 obj = _mesa_select_tex_object(ctx, texUnit, target);
1001 if (!obj) {
1002 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexParameterfv(target)");
1003 return;
1004 }
1005
1006 _mesa_lock_texture(ctx, obj);
1007 switch (pname) {
1008 case GL_TEXTURE_MAG_FILTER:
1009 *params = ENUM_TO_FLOAT(obj->MagFilter);
1010 break;
1011 case GL_TEXTURE_MIN_FILTER:
1012 *params = ENUM_TO_FLOAT(obj->MinFilter);
1013 break;
1014 case GL_TEXTURE_WRAP_S:
1015 *params = ENUM_TO_FLOAT(obj->WrapS);
1016 break;
1017 case GL_TEXTURE_WRAP_T:
1018 *params = ENUM_TO_FLOAT(obj->WrapT);
1019 break;
1020 case GL_TEXTURE_WRAP_R:
1021 *params = ENUM_TO_FLOAT(obj->WrapR);
1022 break;
1023 case GL_TEXTURE_BORDER_COLOR:
1024 params[0] = CLAMP(obj->BorderColor[0], 0.0F, 1.0F);
1025 params[1] = CLAMP(obj->BorderColor[1], 0.0F, 1.0F);
1026 params[2] = CLAMP(obj->BorderColor[2], 0.0F, 1.0F);
1027 params[3] = CLAMP(obj->BorderColor[3], 0.0F, 1.0F);
1028 break;
1029 case GL_TEXTURE_RESIDENT:
1030 {
1031 GLboolean resident;
1032 if (ctx->Driver.IsTextureResident)
1033 resident = ctx->Driver.IsTextureResident(ctx, obj);
1034 else
1035 resident = GL_TRUE;
1036 *params = ENUM_TO_FLOAT(resident);
1037 }
1038 break;
1039 case GL_TEXTURE_PRIORITY:
1040 *params = obj->Priority;
1041 break;
1042 case GL_TEXTURE_MIN_LOD:
1043 *params = obj->MinLod;
1044 break;
1045 case GL_TEXTURE_MAX_LOD:
1046 *params = obj->MaxLod;
1047 break;
1048 case GL_TEXTURE_BASE_LEVEL:
1049 *params = (GLfloat) obj->BaseLevel;
1050 break;
1051 case GL_TEXTURE_MAX_LEVEL:
1052 *params = (GLfloat) obj->MaxLevel;
1053 break;
1054 case GL_TEXTURE_MAX_ANISOTROPY_EXT:
1055 if (ctx->Extensions.EXT_texture_filter_anisotropic) {
1056 *params = obj->MaxAnisotropy;
1057 }
1058 else
1059 error = GL_TRUE;
1060 break;
1061 case GL_TEXTURE_COMPARE_FAIL_VALUE_ARB:
1062 if (ctx->Extensions.ARB_shadow_ambient) {
1063 *params = obj->CompareFailValue;
1064 }
1065 else
1066 error = GL_TRUE;
1067 break;
1068 case GL_GENERATE_MIPMAP_SGIS:
1069 if (ctx->Extensions.SGIS_generate_mipmap) {
1070 *params = (GLfloat) obj->GenerateMipmap;
1071 }
1072 else
1073 error = GL_TRUE;
1074 break;
1075 case GL_TEXTURE_COMPARE_MODE_ARB:
1076 if (ctx->Extensions.ARB_shadow) {
1077 *params = (GLfloat) obj->CompareMode;
1078 }
1079 else
1080 error = GL_TRUE;
1081 break;
1082 case GL_TEXTURE_COMPARE_FUNC_ARB:
1083 if (ctx->Extensions.ARB_shadow) {
1084 *params = (GLfloat) obj->CompareFunc;
1085 }
1086 else
1087 error = GL_TRUE;
1088 break;
1089 case GL_DEPTH_TEXTURE_MODE_ARB:
1090 if (ctx->Extensions.ARB_depth_texture) {
1091 *params = (GLfloat) obj->DepthMode;
1092 }
1093 else
1094 error = GL_TRUE;
1095 break;
1096 case GL_TEXTURE_LOD_BIAS:
1097 if (ctx->Extensions.EXT_texture_lod_bias) {
1098 *params = obj->LodBias;
1099 }
1100 else
1101 error = GL_TRUE;
1102 break;
1103 #ifdef FEATURE_OES_draw_texture
1104 case GL_TEXTURE_CROP_RECT_OES:
1105 params[0] = obj->CropRect[0];
1106 params[1] = obj->CropRect[1];
1107 params[2] = obj->CropRect[2];
1108 params[3] = obj->CropRect[3];
1109 break;
1110 #endif
1111
1112 case GL_TEXTURE_SWIZZLE_R_EXT:
1113 case GL_TEXTURE_SWIZZLE_G_EXT:
1114 case GL_TEXTURE_SWIZZLE_B_EXT:
1115 case GL_TEXTURE_SWIZZLE_A_EXT:
1116 if (ctx->Extensions.EXT_texture_swizzle) {
1117 GLuint comp = pname - GL_TEXTURE_SWIZZLE_R_EXT;
1118 *params = (GLfloat) obj->Swizzle[comp];
1119 }
1120 else {
1121 error = GL_TRUE;
1122 }
1123 break;
1124
1125 case GL_TEXTURE_SWIZZLE_RGBA_EXT:
1126 if (ctx->Extensions.EXT_texture_swizzle) {
1127 GLuint comp;
1128 for (comp = 0; comp < 4; comp++) {
1129 params[comp] = (GLfloat) obj->Swizzle[comp];
1130 }
1131 }
1132 else {
1133 error = GL_TRUE;
1134 }
1135 break;
1136
1137 default:
1138 error = GL_TRUE;
1139 break;
1140 }
1141
1142 if (error)
1143 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexParameterfv(pname=0x%x)",
1144 pname);
1145
1146 _mesa_unlock_texture(ctx, obj);
1147 }
1148
1149
1150 void GLAPIENTRY
1151 _mesa_GetTexParameteriv( GLenum target, GLenum pname, GLint *params )
1152 {
1153 struct gl_texture_unit *texUnit;
1154 struct gl_texture_object *obj;
1155 GLboolean error = GL_FALSE;
1156 GET_CURRENT_CONTEXT(ctx);
1157 ASSERT_OUTSIDE_BEGIN_END(ctx);
1158
1159 if (ctx->Texture.CurrentUnit >= ctx->Const.MaxTextureImageUnits) {
1160 _mesa_error(ctx, GL_INVALID_OPERATION,
1161 "glGetTexParameteriv(current unit)");
1162 return;
1163 }
1164
1165 texUnit = &ctx->Texture.Unit[ctx->Texture.CurrentUnit];
1166
1167 obj = _mesa_select_tex_object(ctx, texUnit, target);
1168 if (!obj) {
1169 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexParameteriv(target)");
1170 return;
1171 }
1172
1173 switch (pname) {
1174 case GL_TEXTURE_MAG_FILTER:
1175 *params = (GLint) obj->MagFilter;
1176 break;;
1177 case GL_TEXTURE_MIN_FILTER:
1178 *params = (GLint) obj->MinFilter;
1179 break;;
1180 case GL_TEXTURE_WRAP_S:
1181 *params = (GLint) obj->WrapS;
1182 break;;
1183 case GL_TEXTURE_WRAP_T:
1184 *params = (GLint) obj->WrapT;
1185 break;;
1186 case GL_TEXTURE_WRAP_R:
1187 *params = (GLint) obj->WrapR;
1188 break;;
1189 case GL_TEXTURE_BORDER_COLOR:
1190 {
1191 GLfloat b[4];
1192 b[0] = CLAMP(obj->BorderColor[0], 0.0F, 1.0F);
1193 b[1] = CLAMP(obj->BorderColor[1], 0.0F, 1.0F);
1194 b[2] = CLAMP(obj->BorderColor[2], 0.0F, 1.0F);
1195 b[3] = CLAMP(obj->BorderColor[3], 0.0F, 1.0F);
1196 params[0] = FLOAT_TO_INT(b[0]);
1197 params[1] = FLOAT_TO_INT(b[1]);
1198 params[2] = FLOAT_TO_INT(b[2]);
1199 params[3] = FLOAT_TO_INT(b[3]);
1200 }
1201 break;;
1202 case GL_TEXTURE_RESIDENT:
1203 {
1204 GLboolean resident;
1205 if (ctx->Driver.IsTextureResident)
1206 resident = ctx->Driver.IsTextureResident(ctx, obj);
1207 else
1208 resident = GL_TRUE;
1209 *params = (GLint) resident;
1210 }
1211 break;;
1212 case GL_TEXTURE_PRIORITY:
1213 *params = FLOAT_TO_INT(obj->Priority);
1214 break;;
1215 case GL_TEXTURE_MIN_LOD:
1216 *params = (GLint) obj->MinLod;
1217 break;;
1218 case GL_TEXTURE_MAX_LOD:
1219 *params = (GLint) obj->MaxLod;
1220 break;;
1221 case GL_TEXTURE_BASE_LEVEL:
1222 *params = obj->BaseLevel;
1223 break;;
1224 case GL_TEXTURE_MAX_LEVEL:
1225 *params = obj->MaxLevel;
1226 break;;
1227 case GL_TEXTURE_MAX_ANISOTROPY_EXT:
1228 if (ctx->Extensions.EXT_texture_filter_anisotropic) {
1229 *params = (GLint) obj->MaxAnisotropy;
1230 }
1231 else {
1232 error = GL_TRUE;
1233 }
1234 break;
1235 case GL_TEXTURE_COMPARE_FAIL_VALUE_ARB:
1236 if (ctx->Extensions.ARB_shadow_ambient) {
1237 *params = (GLint) FLOAT_TO_INT(obj->CompareFailValue);
1238 }
1239 else {
1240 error = GL_TRUE;
1241 }
1242 break;
1243 case GL_GENERATE_MIPMAP_SGIS:
1244 if (ctx->Extensions.SGIS_generate_mipmap) {
1245 *params = (GLint) obj->GenerateMipmap;
1246 }
1247 else {
1248 error = GL_TRUE;
1249 }
1250 break;
1251 case GL_TEXTURE_COMPARE_MODE_ARB:
1252 if (ctx->Extensions.ARB_shadow) {
1253 *params = (GLint) obj->CompareMode;
1254 }
1255 else {
1256 error = GL_TRUE;
1257 }
1258 break;
1259 case GL_TEXTURE_COMPARE_FUNC_ARB:
1260 if (ctx->Extensions.ARB_shadow) {
1261 *params = (GLint) obj->CompareFunc;
1262 }
1263 else {
1264 error = GL_TRUE;
1265 }
1266 break;
1267 case GL_DEPTH_TEXTURE_MODE_ARB:
1268 if (ctx->Extensions.ARB_depth_texture) {
1269 *params = (GLint) obj->DepthMode;
1270 }
1271 else {
1272 error = GL_TRUE;
1273 }
1274 break;
1275 case GL_TEXTURE_LOD_BIAS:
1276 if (ctx->Extensions.EXT_texture_lod_bias) {
1277 *params = (GLint) obj->LodBias;
1278 }
1279 else {
1280 error = GL_TRUE;
1281 }
1282 break;
1283 #ifdef FEATURE_OES_draw_texture
1284 case GL_TEXTURE_CROP_RECT_OES:
1285 params[0] = obj->CropRect[0];
1286 params[1] = obj->CropRect[1];
1287 params[2] = obj->CropRect[2];
1288 params[3] = obj->CropRect[3];
1289 break;
1290 #endif
1291 case GL_TEXTURE_SWIZZLE_R_EXT:
1292 case GL_TEXTURE_SWIZZLE_G_EXT:
1293 case GL_TEXTURE_SWIZZLE_B_EXT:
1294 case GL_TEXTURE_SWIZZLE_A_EXT:
1295 if (ctx->Extensions.EXT_texture_swizzle) {
1296 GLuint comp = pname - GL_TEXTURE_SWIZZLE_R_EXT;
1297 *params = obj->Swizzle[comp];
1298 }
1299 else {
1300 error = GL_TRUE;
1301 }
1302 break;
1303
1304 case GL_TEXTURE_SWIZZLE_RGBA_EXT:
1305 if (ctx->Extensions.EXT_texture_swizzle) {
1306 COPY_4V(params, obj->Swizzle);
1307 }
1308 else {
1309 error = GL_TRUE;
1310 }
1311 break;
1312
1313 default:
1314 ; /* silence warnings */
1315 }
1316
1317 if (error)
1318 _mesa_error(ctx, GL_INVALID_ENUM, "glGetTexParameteriv(pname=0x%x)",
1319 pname);
1320
1321 _mesa_unlock_texture(ctx, obj);
1322 }