a507173b2188f0a087a015f29c1bef2f2b28134c
[mesa.git] / src / mesa / drivers / dri / sis / sis_texstate.c
1 /**************************************************************************
2
3 Copyright 2000 Silicon Integrated Systems Corp, Inc., HsinChu, Taiwan.
4 Copyright 2003 Eric Anholt
5 All Rights Reserved.
6
7 Permission is hereby granted, free of charge, to any person obtaining a
8 copy of this software and associated documentation files (the "Software"),
9 to deal in the Software without restriction, including without limitation
10 on the rights to use, copy, modify, merge, publish, distribute, sub
11 license, and/or sell copies of the Software, and to permit persons to whom
12 the Software is furnished to do so, subject to the following conditions:
13
14 The above copyright notice and this permission notice (including the next
15 paragraph) shall be included in all copies or substantial portions of the
16 Software.
17
18 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20 FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
21 ERIC ANHOLT OR SILICON INTEGRATED SYSTEMS CORP BE LIABLE FOR ANY CLAIM,
22 DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
23 OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
24 USE OR OTHER DEALINGS IN THE SOFTWARE.
25
26 **************************************************************************/
27
28 /*
29 * Authors:
30 * Sung-Ching Lin <sclin@sis.com.tw>
31 * Eric Anholt <anholt@FreeBSD.org>
32 */
33
34 #include "main/glheader.h"
35 #include "main/imports.h"
36 #include "main/colormac.h"
37 #include "main/context.h"
38 #include "main/macros.h"
39
40 #include "sis_context.h"
41 #include "sis_state.h"
42 #include "sis_tex.h"
43 #include "sis_tris.h"
44 #include "sis_alloc.h"
45
46 static GLint TransferTexturePitch (GLint dwPitch);
47
48 /* Handle texenv stuff, called from validate_texture (renderstart) */
49 static void
50 sis_set_texture_env0( GLcontext *ctx, struct gl_texture_object *texObj,
51 int unit )
52 {
53 sisContextPtr smesa = SIS_CONTEXT(ctx);
54 GLubyte c[4];
55
56 __GLSiSHardware *prev = &smesa->prev;
57 __GLSiSHardware *current = &smesa->current;
58
59 struct gl_texture_unit *texture_unit = &ctx->Texture.Unit[unit];
60
61 sisTexObjPtr t = texObj->DriverData;
62
63 switch (texture_unit->EnvMode)
64 {
65 case GL_REPLACE:
66 switch (t->format)
67 {
68 case GL_ALPHA:
69 current->hwTexBlendColor0 = STAGE0_C_CF;
70 current->hwTexBlendAlpha0 = STAGE0_A_AS;
71 break;
72 case GL_LUMINANCE:
73 case GL_RGB:
74 case GL_YCBCR_MESA:
75 current->hwTexBlendColor0 = STAGE0_C_CS;
76 current->hwTexBlendAlpha0 = STAGE0_A_AF;
77 break;
78 case GL_INTENSITY:
79 case GL_LUMINANCE_ALPHA:
80 case GL_RGBA:
81 current->hwTexBlendColor0 = STAGE0_C_CS;
82 current->hwTexBlendAlpha0 = STAGE0_A_AS;
83 break;
84 default:
85 sis_fatal_error("unknown base format 0x%x\n", t->format);
86 }
87 break;
88
89 case GL_MODULATE:
90 switch (t->format)
91 {
92 case GL_ALPHA:
93 current->hwTexBlendColor0 = STAGE0_C_CF;
94 current->hwTexBlendAlpha0 = STAGE0_A_AFAS;
95 break;
96 case GL_LUMINANCE:
97 case GL_RGB:
98 case GL_YCBCR_MESA:
99 current->hwTexBlendColor0 = STAGE0_C_CFCS;
100 current->hwTexBlendAlpha0 = STAGE0_A_AF;
101 break;
102 case GL_INTENSITY:
103 case GL_LUMINANCE_ALPHA:
104 case GL_RGBA:
105 current->hwTexBlendColor0 = STAGE0_C_CFCS;
106 current->hwTexBlendAlpha0 = STAGE0_A_AFAS;
107 break;
108 default:
109 sis_fatal_error("unknown base format 0x%x\n", t->format);
110 }
111 break;
112
113 case GL_DECAL:
114 switch (t->format)
115 {
116 case GL_RGB:
117 case GL_YCBCR_MESA:
118 current->hwTexBlendColor0 = STAGE0_C_CS;
119 current->hwTexBlendAlpha0 = STAGE0_A_AF;
120 break;
121 case GL_RGBA:
122 current->hwTexBlendColor0 = STAGE0_C_CFOMAS_CSAS;
123 current->hwTexBlendAlpha0 = STAGE0_A_AF;
124 break;
125 case GL_ALPHA:
126 case GL_LUMINANCE:
127 case GL_INTENSITY:
128 case GL_LUMINANCE_ALPHA:
129 current->hwTexBlendColor0 = STAGE0_C_CF;
130 current->hwTexBlendAlpha0 = STAGE0_A_AF;
131 break;
132 default:
133 sis_fatal_error("unknown base format 0x%x\n", t->format);
134 }
135 break;
136
137 case GL_BLEND:
138 UNCLAMPED_FLOAT_TO_RGBA_CHAN(c, texture_unit->EnvColor);
139 current->hwTexEnvColor = ((GLint) (c[3])) << 24 |
140 ((GLint) (c[0])) << 16 |
141 ((GLint) (c[1])) << 8 |
142 ((GLint) (c[2]));
143 switch (t->format)
144 {
145 case GL_ALPHA:
146 current->hwTexBlendColor0 = STAGE0_C_CF;
147 current->hwTexBlendAlpha0 = STAGE0_A_AFAS;
148 break;
149 case GL_LUMINANCE:
150 case GL_RGB:
151 case GL_YCBCR_MESA:
152 current->hwTexBlendColor0 = STAGE0_C_CFOMCS_CCCS;
153 current->hwTexBlendAlpha0 = STAGE0_A_AF;
154 break;
155 case GL_INTENSITY:
156 current->hwTexBlendColor0 = STAGE0_C_CFOMCS_CCCS;
157 current->hwTexBlendAlpha0 = STAGE0_A_AFOMAS_ACAS;
158 break;
159 case GL_LUMINANCE_ALPHA:
160 case GL_RGBA:
161 current->hwTexBlendColor0 = STAGE0_C_CFOMCS_CCCS;
162 current->hwTexBlendAlpha0 = STAGE0_A_AFAS;
163 break;
164 default:
165 sis_fatal_error("unknown base format 0x%x\n", t->format);
166 }
167 break;
168
169 default:
170 sis_fatal_error("unknown env mode 0x%x\n", texture_unit->EnvMode);
171 }
172
173 if ((current->hwTexBlendColor0 != prev->hwTexBlendColor0) ||
174 (current->hwTexBlendAlpha0 != prev->hwTexBlendAlpha0) ||
175 (current->hwTexEnvColor != prev->hwTexEnvColor))
176 {
177 prev->hwTexEnvColor = current->hwTexEnvColor;
178 prev->hwTexBlendColor0 = current->hwTexBlendColor0;
179 prev->hwTexBlendAlpha0 = current->hwTexBlendAlpha0;
180 smesa->GlobalFlag |= GFLAG_TEXTUREENV;
181 }
182 }
183
184 /* Handle texenv stuff, called from validate_texture (renderstart) */
185 static void
186 sis_set_texture_env1( GLcontext *ctx, struct gl_texture_object *texObj,
187 int unit)
188 {
189 sisContextPtr smesa = SIS_CONTEXT(ctx);
190 GLubyte c[4];
191
192 __GLSiSHardware *prev = &smesa->prev;
193 __GLSiSHardware *current = &smesa->current;
194
195 struct gl_texture_unit *texture_unit = &ctx->Texture.Unit[unit];
196
197 sisTexObjPtr t = texObj->DriverData;
198
199 switch (texture_unit->EnvMode)
200 {
201 case GL_REPLACE:
202 switch (t->format)
203 {
204 case GL_ALPHA:
205 current->hwTexBlendColor1 = STAGE1_C_CF;
206 current->hwTexBlendAlpha1 = STAGE1_A_AS;
207 break;
208 case GL_LUMINANCE:
209 case GL_RGB:
210 case GL_YCBCR_MESA:
211 current->hwTexBlendColor1 = STAGE1_C_CS;
212 current->hwTexBlendAlpha1 = STAGE1_A_AF;
213 break;
214 case GL_INTENSITY:
215 case GL_LUMINANCE_ALPHA:
216 case GL_RGBA:
217 current->hwTexBlendColor1 = STAGE1_C_CS;
218 current->hwTexBlendAlpha1 = STAGE1_A_AS;
219 break;
220 default:
221 sis_fatal_error("unknown base format 0x%x\n", t->format);
222 }
223 break;
224
225 case GL_MODULATE:
226 switch (t->format)
227 {
228 case GL_ALPHA:
229 current->hwTexBlendColor1 = STAGE1_C_CF;
230 current->hwTexBlendAlpha1 = STAGE1_A_AFAS;
231 break;
232 case GL_LUMINANCE:
233 case GL_RGB:
234 case GL_YCBCR_MESA:
235 current->hwTexBlendColor1 = STAGE1_C_CFCS;
236 current->hwTexBlendAlpha1 = STAGE1_A_AF;
237 break;
238 case GL_INTENSITY:
239 case GL_LUMINANCE_ALPHA:
240 case GL_RGBA:
241 current->hwTexBlendColor1 = STAGE1_C_CFCS;
242 current->hwTexBlendAlpha1 = STAGE1_A_AFAS;
243 break;
244 default:
245 sis_fatal_error("unknown base format 0x%x\n", t->format);
246 }
247 break;
248
249 case GL_DECAL:
250 switch (t->format)
251 {
252 case GL_RGB:
253 case GL_YCBCR_MESA:
254 current->hwTexBlendColor1 = STAGE1_C_CS;
255 current->hwTexBlendAlpha1 = STAGE1_A_AF;
256 break;
257 case GL_RGBA:
258 current->hwTexBlendColor1 = STAGE1_C_CFOMAS_CSAS;
259 current->hwTexBlendAlpha1 = STAGE1_A_AF;
260 break;
261 case GL_ALPHA:
262 case GL_LUMINANCE:
263 case GL_INTENSITY:
264 case GL_LUMINANCE_ALPHA:
265 current->hwTexBlendColor1 = STAGE1_C_CF;
266 current->hwTexBlendAlpha1 = STAGE1_A_AF;
267 break;
268 default:
269 sis_fatal_error("unknown base format 0x%x\n", t->format);
270 }
271 break;
272
273 case GL_BLEND:
274 UNCLAMPED_FLOAT_TO_RGBA_CHAN(c, texture_unit->EnvColor);
275 current->hwTexEnvColor = ((GLint) (c[3])) << 24 |
276 ((GLint) (c[0])) << 16 |
277 ((GLint) (c[1])) << 8 |
278 ((GLint) (c[2]));
279 switch (t->format)
280 {
281 case GL_ALPHA:
282 current->hwTexBlendColor1 = STAGE1_C_CF;
283 current->hwTexBlendAlpha1 = STAGE1_A_AFAS;
284 break;
285 case GL_LUMINANCE:
286 case GL_RGB:
287 case GL_YCBCR_MESA:
288 current->hwTexBlendColor1 = STAGE1_C_CFOMCS_CCCS;
289 current->hwTexBlendAlpha1 = STAGE1_A_AF;
290 break;
291 case GL_INTENSITY:
292 current->hwTexBlendColor1 = STAGE1_C_CFOMCS_CCCS;
293 current->hwTexBlendAlpha1 = STAGE1_A_AFOMAS_ACAS;
294 break;
295 case GL_LUMINANCE_ALPHA:
296 case GL_RGBA:
297 current->hwTexBlendColor1 = STAGE1_C_CFOMCS_CCCS;
298 current->hwTexBlendAlpha1 = STAGE1_A_AFAS;
299 break;
300 default:
301 sis_fatal_error("unknown base format 0x%x\n", t->format);
302 }
303 break;
304
305 default:
306 sis_fatal_error("unknown env mode 0x%x\n", texture_unit->EnvMode);
307 }
308
309 if ((current->hwTexBlendColor1 != prev->hwTexBlendColor1) ||
310 (current->hwTexBlendAlpha1 != prev->hwTexBlendAlpha1) ||
311 (current->hwTexEnvColor != prev->hwTexEnvColor))
312 {
313 prev->hwTexBlendColor1 = current->hwTexBlendColor1;
314 prev->hwTexBlendAlpha1 = current->hwTexBlendAlpha1;
315 prev->hwTexEnvColor = current->hwTexEnvColor;
316 smesa->GlobalFlag |= GFLAG_TEXTUREENV_1;
317 }
318 }
319
320 /* Returns 0 if a software fallback is necessary */
321 static GLboolean
322 sis_set_texobj_parm( GLcontext *ctx, struct gl_texture_object *texObj,
323 int hw_unit )
324 {
325 sisContextPtr smesa = SIS_CONTEXT(ctx);
326 int ok = 1;
327
328 __GLSiSHardware *prev = &smesa->prev;
329 __GLSiSHardware *current = &smesa->current;
330
331 sisTexObjPtr t = texObj->DriverData;
332
333 GLint firstLevel, lastLevel;
334 GLint i;
335
336 current->texture[hw_unit].hwTextureMip = 0UL;
337 current->texture[hw_unit].hwTextureSet = t->hwformat;
338
339 if ((texObj->MinFilter == GL_NEAREST) || (texObj->MinFilter == GL_LINEAR)) {
340 firstLevel = lastLevel = texObj->BaseLevel;
341 } else {
342 /* Compute which mipmap levels we really want to send to the hardware.
343 * This depends on the base image size, GL_TEXTURE_MIN_LOD,
344 * GL_TEXTURE_MAX_LOD, GL_TEXTURE_BASE_LEVEL and GL_TEXTURE_MAX_LEVEL.
345 * Yes, this looks overly complicated, but it's all needed.
346 */
347
348 firstLevel = texObj->BaseLevel + (GLint)(texObj->MinLod + 0.5);
349 firstLevel = MAX2(firstLevel, texObj->BaseLevel);
350 lastLevel = texObj->BaseLevel + (GLint)(texObj->MaxLod + 0.5);
351 lastLevel = MAX2(lastLevel, texObj->BaseLevel);
352 lastLevel = MIN2(lastLevel, texObj->BaseLevel +
353 texObj->Image[0][texObj->BaseLevel]->MaxLog2);
354 lastLevel = MIN2(lastLevel, texObj->MaxLevel);
355 lastLevel = MAX2(firstLevel, lastLevel); /* need at least one level */
356 }
357
358 current->texture[hw_unit].hwTextureSet |= (lastLevel << 8);
359
360 switch (texObj->MagFilter)
361 {
362 case GL_NEAREST:
363 current->texture[hw_unit].hwTextureMip |= TEXTURE_FILTER_NEAREST;
364 break;
365 case GL_LINEAR:
366 current->texture[hw_unit].hwTextureMip |= (TEXTURE_FILTER_LINEAR << 3);
367 break;
368 }
369
370 {
371 GLint b;
372
373 /* The mipmap lod biasing is based on experiment. It seems there's a
374 * limit of around +4/-4 to the bias value; we're being conservative.
375 */
376 b = (GLint) (ctx->Texture.Unit[hw_unit].LodBias * 32.0);
377 if (b > 127)
378 b = 127;
379 else if (b < -128)
380 b = -128;
381
382 current->texture[hw_unit].hwTextureMip |= ((b << 4) &
383 MASK_TextureMipmapLodBias);
384 }
385
386 switch (texObj->MinFilter)
387 {
388 case GL_NEAREST:
389 current->texture[hw_unit].hwTextureMip |= TEXTURE_FILTER_NEAREST;
390 break;
391 case GL_LINEAR:
392 current->texture[hw_unit].hwTextureMip |= TEXTURE_FILTER_LINEAR;
393 break;
394 case GL_NEAREST_MIPMAP_NEAREST:
395 current->texture[hw_unit].hwTextureMip |=
396 TEXTURE_FILTER_NEAREST_MIP_NEAREST;
397 break;
398 case GL_NEAREST_MIPMAP_LINEAR:
399 current->texture[hw_unit].hwTextureMip |=
400 TEXTURE_FILTER_NEAREST_MIP_LINEAR;
401 break;
402 case GL_LINEAR_MIPMAP_NEAREST:
403 current->texture[hw_unit].hwTextureMip |=
404 TEXTURE_FILTER_LINEAR_MIP_NEAREST;
405 break;
406 case GL_LINEAR_MIPMAP_LINEAR:
407 current->texture[hw_unit].hwTextureMip |=
408 TEXTURE_FILTER_LINEAR_MIP_LINEAR;
409 break;
410 }
411
412 switch (texObj->WrapS)
413 {
414 case GL_REPEAT:
415 current->texture[hw_unit].hwTextureSet |= MASK_TextureWrapU;
416 break;
417 case GL_MIRRORED_REPEAT:
418 current->texture[hw_unit].hwTextureSet |= MASK_TextureMirrorU;
419 break;
420 case GL_CLAMP:
421 current->texture[hw_unit].hwTextureSet |= MASK_TextureClampU;
422 /* XXX: GL_CLAMP isn't conformant, but falling back makes the situation
423 * worse in other programs at the moment.
424 */
425 /*ok = 0;*/
426 break;
427 case GL_CLAMP_TO_EDGE:
428 current->texture[hw_unit].hwTextureSet |= MASK_TextureClampU;
429 break;
430 case GL_CLAMP_TO_BORDER:
431 current->texture[hw_unit].hwTextureSet |= MASK_TextureBorderU;
432 break;
433 }
434
435 switch (texObj->WrapT)
436 {
437 case GL_REPEAT:
438 current->texture[hw_unit].hwTextureSet |= MASK_TextureWrapV;
439 break;
440 case GL_MIRRORED_REPEAT:
441 current->texture[hw_unit].hwTextureSet |= MASK_TextureMirrorV;
442 break;
443 case GL_CLAMP:
444 current->texture[hw_unit].hwTextureSet |= MASK_TextureClampV;
445 /* XXX: GL_CLAMP isn't conformant, but falling back makes the situation
446 * worse in other programs at the moment.
447 */
448 /*ok = 0;*/
449 break;
450 case GL_CLAMP_TO_EDGE:
451 current->texture[hw_unit].hwTextureSet |= MASK_TextureClampV;
452 break;
453 case GL_CLAMP_TO_BORDER:
454 current->texture[hw_unit].hwTextureSet |= MASK_TextureBorderV;
455 break;
456 }
457
458 {
459 GLubyte c[4];
460 CLAMPED_FLOAT_TO_UBYTE(c[0], texObj->BorderColor[0]);
461 CLAMPED_FLOAT_TO_UBYTE(c[1], texObj->BorderColor[1]);
462 CLAMPED_FLOAT_TO_UBYTE(c[2], texObj->BorderColor[2]);
463 CLAMPED_FLOAT_TO_UBYTE(c[3], texObj->BorderColor[3]);
464
465 current->texture[hw_unit].hwTextureBorderColor =
466 PACK_COLOR_8888(c[3], c[0], c[1], c[2]);
467 }
468
469 if (current->texture[hw_unit].hwTextureBorderColor !=
470 prev->texture[hw_unit].hwTextureBorderColor)
471 {
472 prev->texture[hw_unit].hwTextureBorderColor =
473 current->texture[hw_unit].hwTextureBorderColor;
474 if (hw_unit == 1)
475 smesa->GlobalFlag |= GFLAG_TEXBORDERCOLOR_1;
476 else
477 smesa->GlobalFlag |= GFLAG_TEXBORDERCOLOR;
478 }
479
480 current->texture[hw_unit].hwTextureSet |=
481 texObj->Image[0][firstLevel]->WidthLog2 << 4;
482 current->texture[hw_unit].hwTextureSet |=
483 texObj->Image[0][firstLevel]->HeightLog2;
484
485 if (hw_unit == 0)
486 smesa->GlobalFlag |= GFLAG_TEXTUREADDRESS;
487 else
488 smesa->GlobalFlag |= GFLAG_TEXTUREADDRESS_1;
489
490 for (i = firstLevel; i <= lastLevel; i++)
491 {
492 GLuint texOffset = 0;
493 GLuint texPitch = TransferTexturePitch( t->image[i].pitch );
494
495 switch (t->image[i].memType)
496 {
497 case VIDEO_TYPE:
498 texOffset = ((unsigned long)t->image[i].Data - (unsigned long)smesa->FbBase);
499 break;
500 case AGP_TYPE:
501 texOffset = ((unsigned long)t->image[i].Data - (unsigned long)smesa->AGPBase) +
502 (unsigned long) smesa->AGPAddr;
503 current->texture[hw_unit].hwTextureMip |=
504 (MASK_TextureLevel0InSystem << i);
505 break;
506 }
507
508 switch (i)
509 {
510 case 0:
511 prev->texture[hw_unit].texOffset0 = texOffset;
512 prev->texture[hw_unit].texPitch01 = texPitch << 16;
513 break;
514 case 1:
515 prev->texture[hw_unit].texOffset1 = texOffset;
516 prev->texture[hw_unit].texPitch01 |= texPitch;
517 break;
518 case 2:
519 prev->texture[hw_unit].texOffset2 = texOffset;
520 prev->texture[hw_unit].texPitch23 = texPitch << 16;
521 break;
522 case 3:
523 prev->texture[hw_unit].texOffset3 = texOffset;
524 prev->texture[hw_unit].texPitch23 |= texPitch;
525 break;
526 case 4:
527 prev->texture[hw_unit].texOffset4 = texOffset;
528 prev->texture[hw_unit].texPitch45 = texPitch << 16;
529 break;
530 case 5:
531 prev->texture[hw_unit].texOffset5 = texOffset;
532 prev->texture[hw_unit].texPitch45 |= texPitch;
533 break;
534 case 6:
535 prev->texture[hw_unit].texOffset6 = texOffset;
536 prev->texture[hw_unit].texPitch67 = texPitch << 16;
537 break;
538 case 7:
539 prev->texture[hw_unit].texOffset7 = texOffset;
540 prev->texture[hw_unit].texPitch67 |= texPitch;
541 break;
542 case 8:
543 prev->texture[hw_unit].texOffset8 = texOffset;
544 prev->texture[hw_unit].texPitch89 = texPitch << 16;
545 break;
546 case 9:
547 prev->texture[hw_unit].texOffset9 = texOffset;
548 prev->texture[hw_unit].texPitch89 |= texPitch;
549 break;
550 case 10:
551 prev->texture[hw_unit].texOffset10 = texOffset;
552 prev->texture[hw_unit].texPitch10 = texPitch << 16;
553 break;
554 case 11:
555 prev->texture[hw_unit].texOffset11 = texOffset;
556 prev->texture[hw_unit].texPitch10 |= texPitch;
557 break;
558 }
559 }
560
561 if (current->texture[hw_unit].hwTextureSet !=
562 prev->texture[hw_unit].hwTextureSet)
563 {
564 prev->texture[hw_unit].hwTextureSet =
565 current->texture[hw_unit].hwTextureSet;
566 if (hw_unit == 1)
567 smesa->GlobalFlag |= CFLAG_TEXTURERESET_1;
568 else
569 smesa->GlobalFlag |= CFLAG_TEXTURERESET;
570 }
571 if (current->texture[hw_unit].hwTextureMip !=
572 prev->texture[hw_unit].hwTextureMip)
573 {
574 prev->texture[hw_unit].hwTextureMip =
575 current->texture[hw_unit].hwTextureMip;
576 if (hw_unit == 1)
577 smesa->GlobalFlag |= GFLAG_TEXTUREMIPMAP_1;
578 else
579 smesa->GlobalFlag |= GFLAG_TEXTUREMIPMAP;
580 }
581
582 return ok;
583 }
584
585 /* Disable a texture unit, called from validate_texture */
586 static void
587 sis_reset_texture_env (GLcontext *ctx, int hw_unit)
588 {
589 sisContextPtr smesa = SIS_CONTEXT(ctx);
590
591 __GLSiSHardware *prev = &smesa->prev;
592 __GLSiSHardware *current = &smesa->current;
593
594 if (hw_unit == 1)
595 {
596 current->hwTexBlendColor1 = STAGE1_C_CF;
597 current->hwTexBlendAlpha1 = STAGE1_A_AF;
598
599 if ((current->hwTexBlendColor1 != prev->hwTexBlendColor1) ||
600 (current->hwTexBlendAlpha1 != prev->hwTexBlendAlpha1) ||
601 (current->hwTexEnvColor != prev->hwTexEnvColor))
602 {
603 prev->hwTexBlendColor1 = current->hwTexBlendColor1;
604 prev->hwTexBlendAlpha1 = current->hwTexBlendAlpha1;
605 prev->hwTexEnvColor = current->hwTexEnvColor;
606 smesa->GlobalFlag |= GFLAG_TEXTUREENV_1;
607 }
608 } else {
609 current->hwTexBlendColor0 = STAGE0_C_CF;
610 current->hwTexBlendAlpha0 = STAGE0_A_AF;
611
612 if ((current->hwTexBlendColor0 != prev->hwTexBlendColor0) ||
613 (current->hwTexBlendAlpha0 != prev->hwTexBlendAlpha0) ||
614 (current->hwTexEnvColor != prev->hwTexEnvColor))
615 {
616 prev->hwTexBlendColor0 = current->hwTexBlendColor0;
617 prev->hwTexBlendAlpha0 = current->hwTexBlendAlpha0;
618 prev->hwTexEnvColor = current->hwTexEnvColor;
619 smesa->GlobalFlag |= GFLAG_TEXTUREENV;
620 }
621 }
622 }
623
624 static void updateTextureUnit( GLcontext *ctx, int unit )
625 {
626 sisContextPtr smesa = SIS_CONTEXT( ctx );
627 const struct gl_texture_unit *texUnit = &ctx->Texture.Unit[unit];
628 struct gl_texture_object *texObj = texUnit->_Current;
629 GLint fallbackbit;
630
631 if (unit == 0)
632 fallbackbit = SIS_FALLBACK_TEXTURE0;
633 else
634 fallbackbit = SIS_FALLBACK_TEXTURE1;
635
636 if (texUnit->_ReallyEnabled & (TEXTURE_1D_BIT | TEXTURE_2D_BIT)) {
637 if (smesa->TexStates[unit] & NEW_TEXTURING) {
638 GLboolean ok;
639
640 ok = sis_set_texobj_parm (ctx, texObj, unit);
641 FALLBACK( smesa, fallbackbit, !ok );
642 }
643 if (smesa->TexStates[unit] & NEW_TEXTURE_ENV) {
644 if (unit == 0)
645 sis_set_texture_env0( ctx, texObj, unit );
646 else
647 sis_set_texture_env1( ctx, texObj, unit );
648 }
649 smesa->TexStates[unit] = 0;
650 } else if ( texUnit->_ReallyEnabled ) {
651 /* fallback */
652 FALLBACK( smesa, fallbackbit, 1 );
653 } else {
654 sis_reset_texture_env( ctx, unit );
655 FALLBACK( smesa, fallbackbit, 0 );
656 }
657 }
658
659
660 void sisUpdateTextureState( GLcontext *ctx )
661 {
662 sisContextPtr smesa = SIS_CONTEXT( ctx );
663 int i;
664 __GLSiSHardware *current = &smesa->current;
665
666 #if 1
667 /* TODO : if unmark these, error in multitexture */ /* XXX */
668 for (i = 0; i < SIS_MAX_TEXTURES; i++)
669 smesa->TexStates[i] |= (NEW_TEXTURING | NEW_TEXTURE_ENV);
670 #endif
671
672 updateTextureUnit( ctx, 0 );
673 updateTextureUnit( ctx, 1 );
674
675 /* XXX Issues with the 2nd unit but not the first being enabled? */
676 if ( ctx->Texture.Unit[0]._ReallyEnabled &
677 (TEXTURE_1D_BIT | TEXTURE_2D_BIT) ||
678 ctx->Texture.Unit[1]._ReallyEnabled &
679 (TEXTURE_1D_BIT | TEXTURE_2D_BIT) )
680 {
681 current->hwCapEnable |= MASK_TextureEnable;
682 current->hwCapEnable &= ~MASK_TextureNumUsed;
683 if (ctx->Texture.Unit[1]._ReallyEnabled)
684 current->hwCapEnable |= 0x00002000;
685 else
686 current->hwCapEnable |= 0x00001000;
687 } else {
688 current->hwCapEnable &= ~MASK_TextureEnable;
689 }
690 }
691
692 static GLint
693 BitScanForward( GLshort w )
694 {
695 GLint i;
696
697 for (i = 0; i < 16; i++) {
698 if (w & (1 << i))
699 break;
700 }
701 return i;
702 }
703
704 static GLint
705 TransferTexturePitch( GLint dwPitch )
706 {
707 GLint dwRet, i;
708
709 i = BitScanForward( (GLshort)dwPitch );
710 dwRet = dwPitch >> i;
711 dwRet |= i << 9;
712 return dwRet;
713 }