r3xx/r5xx: Enable ARB_point_parameters.
[mesa.git] / src / mesa / drivers / dri / r300 / r300_state.c
1 /*
2 Copyright (C) The Weather Channel, Inc. 2002.
3 Copyright (C) 2004 Nicolai Haehnle.
4 All Rights Reserved.
5
6 The Weather Channel (TM) funded Tungsten Graphics to develop the
7 initial release of the Radeon 8500 driver under the XFree86 license.
8 This notice must be preserved.
9
10 Permission is hereby granted, free of charge, to any person obtaining
11 a copy of this software and associated documentation files (the
12 "Software"), to deal in the Software without restriction, including
13 without limitation the rights to use, copy, modify, merge, publish,
14 distribute, sublicense, and/or sell copies of the Software, and to
15 permit persons to whom the Software is furnished to do so, subject to
16 the following conditions:
17
18 The above copyright notice and this permission notice (including the
19 next paragraph) shall be included in all copies or substantial
20 portions of the Software.
21
22 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
23 EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
24 MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
25 IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE
26 LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
27 OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
28 WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29
30 **************************************************************************/
31
32 /**
33 * \file
34 *
35 * \author Nicolai Haehnle <prefect_@gmx.net>
36 */
37
38 #include "glheader.h"
39 #include "state.h"
40 #include "imports.h"
41 #include "enums.h"
42 #include "macros.h"
43 #include "context.h"
44 #include "dd.h"
45 #include "simple_list.h"
46
47 #include "api_arrayelt.h"
48 #include "swrast/swrast.h"
49 #include "swrast_setup/swrast_setup.h"
50 #include "shader/prog_parameter.h"
51 #include "shader/prog_statevars.h"
52 #include "vbo/vbo.h"
53 #include "tnl/tnl.h"
54 #include "texformat.h"
55
56 #include "radeon_ioctl.h"
57 #include "radeon_state.h"
58 #include "r300_context.h"
59 #include "r300_ioctl.h"
60 #include "r300_state.h"
61 #include "r300_reg.h"
62 #include "r300_emit.h"
63 #include "r300_fragprog.h"
64 #include "r300_tex.h"
65
66 #include "drirenderbuffer.h"
67
68 extern int future_hw_tcl_on;
69 extern void _tnl_UpdateFixedFunctionProgram(GLcontext * ctx);
70
71 static void r300BlendColor(GLcontext * ctx, const GLfloat cf[4])
72 {
73 GLubyte color[4];
74 r300ContextPtr rmesa = R300_CONTEXT(ctx);
75
76 R300_STATECHANGE(rmesa, blend_color);
77
78 CLAMPED_FLOAT_TO_UBYTE(color[0], cf[0]);
79 CLAMPED_FLOAT_TO_UBYTE(color[1], cf[1]);
80 CLAMPED_FLOAT_TO_UBYTE(color[2], cf[2]);
81 CLAMPED_FLOAT_TO_UBYTE(color[3], cf[3]);
82
83 rmesa->hw.blend_color.cmd[1] = PACK_COLOR_8888(color[3], color[0],
84 color[1], color[2]);
85 rmesa->hw.blend_color.cmd[2] = 0;
86 rmesa->hw.blend_color.cmd[3] = 0;
87 }
88
89 /**
90 * Calculate the hardware blend factor setting. This same function is used
91 * for source and destination of both alpha and RGB.
92 *
93 * \returns
94 * The hardware register value for the specified blend factor. This value
95 * will need to be shifted into the correct position for either source or
96 * destination factor.
97 *
98 * \todo
99 * Since the two cases where source and destination are handled differently
100 * are essentially error cases, they should never happen. Determine if these
101 * cases can be removed.
102 */
103 static int blend_factor(GLenum factor, GLboolean is_src)
104 {
105 switch (factor) {
106 case GL_ZERO:
107 return R300_BLEND_GL_ZERO;
108 break;
109 case GL_ONE:
110 return R300_BLEND_GL_ONE;
111 break;
112 case GL_DST_COLOR:
113 return R300_BLEND_GL_DST_COLOR;
114 break;
115 case GL_ONE_MINUS_DST_COLOR:
116 return R300_BLEND_GL_ONE_MINUS_DST_COLOR;
117 break;
118 case GL_SRC_COLOR:
119 return R300_BLEND_GL_SRC_COLOR;
120 break;
121 case GL_ONE_MINUS_SRC_COLOR:
122 return R300_BLEND_GL_ONE_MINUS_SRC_COLOR;
123 break;
124 case GL_SRC_ALPHA:
125 return R300_BLEND_GL_SRC_ALPHA;
126 break;
127 case GL_ONE_MINUS_SRC_ALPHA:
128 return R300_BLEND_GL_ONE_MINUS_SRC_ALPHA;
129 break;
130 case GL_DST_ALPHA:
131 return R300_BLEND_GL_DST_ALPHA;
132 break;
133 case GL_ONE_MINUS_DST_ALPHA:
134 return R300_BLEND_GL_ONE_MINUS_DST_ALPHA;
135 break;
136 case GL_SRC_ALPHA_SATURATE:
137 return (is_src) ? R300_BLEND_GL_SRC_ALPHA_SATURATE :
138 R300_BLEND_GL_ZERO;
139 break;
140 case GL_CONSTANT_COLOR:
141 return R300_BLEND_GL_CONST_COLOR;
142 break;
143 case GL_ONE_MINUS_CONSTANT_COLOR:
144 return R300_BLEND_GL_ONE_MINUS_CONST_COLOR;
145 break;
146 case GL_CONSTANT_ALPHA:
147 return R300_BLEND_GL_CONST_ALPHA;
148 break;
149 case GL_ONE_MINUS_CONSTANT_ALPHA:
150 return R300_BLEND_GL_ONE_MINUS_CONST_ALPHA;
151 break;
152 default:
153 fprintf(stderr, "unknown blend factor %x\n", factor);
154 return (is_src) ? R300_BLEND_GL_ONE : R300_BLEND_GL_ZERO;
155 break;
156 }
157 }
158
159 /**
160 * Sets both the blend equation and the blend function.
161 * This is done in a single
162 * function because some blend equations (i.e., \c GL_MIN and \c GL_MAX)
163 * change the interpretation of the blend function.
164 * Also, make sure that blend function and blend equation are set to their
165 * default value if color blending is not enabled, since at least blend
166 * equations GL_MIN and GL_FUNC_REVERSE_SUBTRACT will cause wrong results
167 * otherwise for unknown reasons.
168 */
169
170 /* helper function */
171 static void r300SetBlendCntl(r300ContextPtr r300, int func, int eqn,
172 int cbits, int funcA, int eqnA)
173 {
174 GLuint new_ablend, new_cblend;
175
176 #if 0
177 fprintf(stderr,
178 "eqnA=%08x funcA=%08x eqn=%08x func=%08x cbits=%08x\n",
179 eqnA, funcA, eqn, func, cbits);
180 #endif
181 new_ablend = eqnA | funcA;
182 new_cblend = eqn | func;
183
184 /* Some blend factor combinations don't seem to work when the
185 * BLEND_NO_SEPARATE bit is set.
186 *
187 * Especially problematic candidates are the ONE_MINUS_* flags,
188 * but I can't see a real pattern.
189 */
190 #if 0
191 if (new_ablend == new_cblend) {
192 new_cblend |= R300_DISCARD_SRC_PIXELS_SRC_ALPHA_0;
193 }
194 #endif
195 new_cblend |= cbits;
196
197 if ((new_ablend != r300->hw.bld.cmd[R300_BLD_ABLEND]) ||
198 (new_cblend != r300->hw.bld.cmd[R300_BLD_CBLEND])) {
199 R300_STATECHANGE(r300, bld);
200 r300->hw.bld.cmd[R300_BLD_ABLEND] = new_ablend;
201 r300->hw.bld.cmd[R300_BLD_CBLEND] = new_cblend;
202 }
203 }
204
205 static void r300SetBlendState(GLcontext * ctx)
206 {
207 r300ContextPtr r300 = R300_CONTEXT(ctx);
208 int func = (R300_BLEND_GL_ONE << R300_SRC_BLEND_SHIFT) |
209 (R300_BLEND_GL_ZERO << R300_DST_BLEND_SHIFT);
210 int eqn = R300_COMB_FCN_ADD_CLAMP;
211 int funcA = (R300_BLEND_GL_ONE << R300_SRC_BLEND_SHIFT) |
212 (R300_BLEND_GL_ZERO << R300_DST_BLEND_SHIFT);
213 int eqnA = R300_COMB_FCN_ADD_CLAMP;
214
215 if (RGBA_LOGICOP_ENABLED(ctx) || !ctx->Color.BlendEnabled) {
216 r300SetBlendCntl(r300, func, eqn, 0, func, eqn);
217 return;
218 }
219
220 func =
221 (blend_factor(ctx->Color.BlendSrcRGB, GL_TRUE) <<
222 R300_SRC_BLEND_SHIFT) | (blend_factor(ctx->Color.BlendDstRGB,
223 GL_FALSE) <<
224 R300_DST_BLEND_SHIFT);
225
226 switch (ctx->Color.BlendEquationRGB) {
227 case GL_FUNC_ADD:
228 eqn = R300_COMB_FCN_ADD_CLAMP;
229 break;
230
231 case GL_FUNC_SUBTRACT:
232 eqn = R300_COMB_FCN_SUB_CLAMP;
233 break;
234
235 case GL_FUNC_REVERSE_SUBTRACT:
236 eqn = R300_COMB_FCN_RSUB_CLAMP;
237 break;
238
239 case GL_MIN:
240 eqn = R300_COMB_FCN_MIN;
241 func = (R300_BLEND_GL_ONE << R300_SRC_BLEND_SHIFT) |
242 (R300_BLEND_GL_ONE << R300_DST_BLEND_SHIFT);
243 break;
244
245 case GL_MAX:
246 eqn = R300_COMB_FCN_MAX;
247 func = (R300_BLEND_GL_ONE << R300_SRC_BLEND_SHIFT) |
248 (R300_BLEND_GL_ONE << R300_DST_BLEND_SHIFT);
249 break;
250
251 default:
252 fprintf(stderr,
253 "[%s:%u] Invalid RGB blend equation (0x%04x).\n",
254 __FUNCTION__, __LINE__, ctx->Color.BlendEquationRGB);
255 return;
256 }
257
258 funcA =
259 (blend_factor(ctx->Color.BlendSrcA, GL_TRUE) <<
260 R300_SRC_BLEND_SHIFT) | (blend_factor(ctx->Color.BlendDstA,
261 GL_FALSE) <<
262 R300_DST_BLEND_SHIFT);
263
264 switch (ctx->Color.BlendEquationA) {
265 case GL_FUNC_ADD:
266 eqnA = R300_COMB_FCN_ADD_CLAMP;
267 break;
268
269 case GL_FUNC_SUBTRACT:
270 eqnA = R300_COMB_FCN_SUB_CLAMP;
271 break;
272
273 case GL_FUNC_REVERSE_SUBTRACT:
274 eqnA = R300_COMB_FCN_RSUB_CLAMP;
275 break;
276
277 case GL_MIN:
278 eqnA = R300_COMB_FCN_MIN;
279 funcA = (R300_BLEND_GL_ONE << R300_SRC_BLEND_SHIFT) |
280 (R300_BLEND_GL_ONE << R300_DST_BLEND_SHIFT);
281 break;
282
283 case GL_MAX:
284 eqnA = R300_COMB_FCN_MAX;
285 funcA = (R300_BLEND_GL_ONE << R300_SRC_BLEND_SHIFT) |
286 (R300_BLEND_GL_ONE << R300_DST_BLEND_SHIFT);
287 break;
288
289 default:
290 fprintf(stderr,
291 "[%s:%u] Invalid A blend equation (0x%04x).\n",
292 __FUNCTION__, __LINE__, ctx->Color.BlendEquationA);
293 return;
294 }
295
296 r300SetBlendCntl(r300,
297 func, eqn,
298 (R300_SEPARATE_ALPHA_ENABLE |
299 R300_READ_ENABLE |
300 R300_ALPHA_BLEND_ENABLE), funcA, eqnA);
301 }
302
303 static void r300BlendEquationSeparate(GLcontext * ctx,
304 GLenum modeRGB, GLenum modeA)
305 {
306 r300SetBlendState(ctx);
307 }
308
309 static void r300BlendFuncSeparate(GLcontext * ctx,
310 GLenum sfactorRGB, GLenum dfactorRGB,
311 GLenum sfactorA, GLenum dfactorA)
312 {
313 r300SetBlendState(ctx);
314 }
315
316 static void r300ClipPlane( GLcontext *ctx, GLenum plane, const GLfloat *eq )
317 {
318 r300ContextPtr rmesa = R300_CONTEXT(ctx);
319 GLint p;
320 GLint *ip;
321
322 /* no VAP UCP on non-TCL chipsets */
323 if (!(rmesa->radeon.radeonScreen->chip_flags & RADEON_CHIPSET_TCL))
324 return;
325
326 p = (GLint) plane - (GLint) GL_CLIP_PLANE0;
327 ip = (GLint *)ctx->Transform._ClipUserPlane[p];
328
329 R300_STATECHANGE( rmesa, vpucp[p] );
330 rmesa->hw.vpucp[p].cmd[R300_VPUCP_X] = ip[0];
331 rmesa->hw.vpucp[p].cmd[R300_VPUCP_Y] = ip[1];
332 rmesa->hw.vpucp[p].cmd[R300_VPUCP_Z] = ip[2];
333 rmesa->hw.vpucp[p].cmd[R300_VPUCP_W] = ip[3];
334 }
335
336 static void r300SetClipPlaneState(GLcontext * ctx, GLenum cap, GLboolean state)
337 {
338 r300ContextPtr r300 = R300_CONTEXT(ctx);
339 GLuint p;
340
341 /* no VAP UCP on non-TCL chipsets */
342 if (!(r300->radeon.radeonScreen->chip_flags & RADEON_CHIPSET_TCL))
343 return;
344
345 p = cap - GL_CLIP_PLANE0;
346 R300_STATECHANGE(r300, vap_clip_cntl);
347 if (state) {
348 r300->hw.vap_clip_cntl.cmd[1] |= (R300_VAP_UCP_ENABLE_0 << p);
349 r300ClipPlane(ctx, cap, NULL);
350 } else {
351 r300->hw.vap_clip_cntl.cmd[1] &= ~(R300_VAP_UCP_ENABLE_0 << p);
352 }
353 }
354
355 /**
356 * Update our tracked culling state based on Mesa's state.
357 */
358 static void r300UpdateCulling(GLcontext * ctx)
359 {
360 r300ContextPtr r300 = R300_CONTEXT(ctx);
361 uint32_t val = 0;
362
363 if (ctx->Polygon.CullFlag) {
364 switch (ctx->Polygon.CullFaceMode) {
365 case GL_FRONT:
366 val = R300_CULL_FRONT;
367 break;
368 case GL_BACK:
369 val = R300_CULL_BACK;
370 break;
371 case GL_FRONT_AND_BACK:
372 val = R300_CULL_FRONT | R300_CULL_BACK;
373 break;
374 default:
375 break;
376 }
377 }
378
379 switch (ctx->Polygon.FrontFace) {
380 case GL_CW:
381 val |= R300_FRONT_FACE_CW;
382 break;
383 case GL_CCW:
384 val |= R300_FRONT_FACE_CCW;
385 break;
386 default:
387 break;
388 }
389
390 R300_STATECHANGE(r300, cul);
391 r300->hw.cul.cmd[R300_CUL_CULL] = val;
392 }
393
394 static void r300SetPolygonOffsetState(GLcontext * ctx, GLboolean state)
395 {
396 r300ContextPtr r300 = R300_CONTEXT(ctx);
397
398 R300_STATECHANGE(r300, occlusion_cntl);
399 if (state) {
400 r300->hw.occlusion_cntl.cmd[1] |= (3 << 0);
401 } else {
402 r300->hw.occlusion_cntl.cmd[1] &= ~(3 << 0);
403 }
404 }
405
406 static GLboolean current_fragment_program_writes_depth(GLcontext* ctx)
407 {
408 r300ContextPtr r300 = R300_CONTEXT(ctx);
409
410 if (r300->radeon.radeonScreen->chip_family < CHIP_FAMILY_RV515) {
411 struct r300_fragment_program *fp = (struct r300_fragment_program *)
412 (char *)ctx->FragmentProgram._Current;
413 return (fp && fp->WritesDepth);
414 } else {
415 struct r500_fragment_program* fp =
416 (struct r500_fragment_program*)(char*)
417 ctx->FragmentProgram._Current;
418 return (fp && fp->writes_depth);
419 }
420 }
421
422 static void r300SetEarlyZState(GLcontext * ctx)
423 {
424 r300ContextPtr r300 = R300_CONTEXT(ctx);
425 GLuint topZ = R300_ZTOP_ENABLE;
426
427 if (ctx->Color.AlphaEnabled && ctx->Color.AlphaFunc != GL_ALWAYS)
428 topZ = R300_ZTOP_DISABLE;
429 if (current_fragment_program_writes_depth(ctx))
430 topZ = R300_ZTOP_DISABLE;
431
432 if (topZ != r300->hw.zstencil_format.cmd[2]) {
433 /* Note: This completely reemits the stencil format.
434 * I have not tested whether this is strictly necessary,
435 * or if emitting a write to ZB_ZTOP is enough.
436 */
437 R300_STATECHANGE(r300, zstencil_format);
438 r300->hw.zstencil_format.cmd[2] = topZ;
439 }
440 }
441
442 static void r300SetAlphaState(GLcontext * ctx)
443 {
444 r300ContextPtr r300 = R300_CONTEXT(ctx);
445 GLubyte refByte;
446 uint32_t pp_misc = 0x0;
447 GLboolean really_enabled = ctx->Color.AlphaEnabled;
448
449 CLAMPED_FLOAT_TO_UBYTE(refByte, ctx->Color.AlphaRef);
450
451 switch (ctx->Color.AlphaFunc) {
452 case GL_NEVER:
453 pp_misc |= R300_FG_ALPHA_FUNC_NEVER;
454 break;
455 case GL_LESS:
456 pp_misc |= R300_FG_ALPHA_FUNC_LESS;
457 break;
458 case GL_EQUAL:
459 pp_misc |= R300_FG_ALPHA_FUNC_EQUAL;
460 break;
461 case GL_LEQUAL:
462 pp_misc |= R300_FG_ALPHA_FUNC_LE;
463 break;
464 case GL_GREATER:
465 pp_misc |= R300_FG_ALPHA_FUNC_GREATER;
466 break;
467 case GL_NOTEQUAL:
468 pp_misc |= R300_FG_ALPHA_FUNC_NOTEQUAL;
469 break;
470 case GL_GEQUAL:
471 pp_misc |= R300_FG_ALPHA_FUNC_GE;
472 break;
473 case GL_ALWAYS:
474 /*pp_misc |= FG_ALPHA_FUNC_ALWAYS; */
475 really_enabled = GL_FALSE;
476 break;
477 }
478
479 if (really_enabled) {
480 pp_misc |= R300_FG_ALPHA_FUNC_ENABLE;
481 pp_misc |= R500_FG_ALPHA_FUNC_8BIT;
482 pp_misc |= (refByte & R300_FG_ALPHA_FUNC_VAL_MASK);
483 } else {
484 pp_misc = 0x0;
485 }
486
487 R300_STATECHANGE(r300, at);
488 r300->hw.at.cmd[R300_AT_ALPHA_TEST] = pp_misc;
489 r300->hw.at.cmd[R300_AT_UNKNOWN] = 0;
490
491 r300SetEarlyZState(ctx);
492 }
493
494 static void r300AlphaFunc(GLcontext * ctx, GLenum func, GLfloat ref)
495 {
496 (void)func;
497 (void)ref;
498 r300SetAlphaState(ctx);
499 }
500
501 static int translate_func(int func)
502 {
503 switch (func) {
504 case GL_NEVER:
505 return R300_ZS_NEVER;
506 case GL_LESS:
507 return R300_ZS_LESS;
508 case GL_EQUAL:
509 return R300_ZS_EQUAL;
510 case GL_LEQUAL:
511 return R300_ZS_LEQUAL;
512 case GL_GREATER:
513 return R300_ZS_GREATER;
514 case GL_NOTEQUAL:
515 return R300_ZS_NOTEQUAL;
516 case GL_GEQUAL:
517 return R300_ZS_GEQUAL;
518 case GL_ALWAYS:
519 return R300_ZS_ALWAYS;
520 }
521 return 0;
522 }
523
524 static void r300SetDepthState(GLcontext * ctx)
525 {
526 r300ContextPtr r300 = R300_CONTEXT(ctx);
527
528 R300_STATECHANGE(r300, zs);
529 r300->hw.zs.cmd[R300_ZS_CNTL_0] &= R300_STENCIL_ENABLE|R300_STENCIL_FRONT_BACK;
530 r300->hw.zs.cmd[R300_ZS_CNTL_1] &= ~(R300_ZS_MASK << R300_Z_FUNC_SHIFT);
531
532 if (ctx->Depth.Test) {
533 r300->hw.zs.cmd[R300_ZS_CNTL_0] |= R300_Z_ENABLE;
534 if (ctx->Depth.Mask)
535 r300->hw.zs.cmd[R300_ZS_CNTL_0] |= R300_Z_WRITE_ENABLE;
536 r300->hw.zs.cmd[R300_ZS_CNTL_1] |=
537 translate_func(ctx->Depth.Func) << R300_Z_FUNC_SHIFT;
538 }
539
540 r300SetEarlyZState(ctx);
541 }
542
543 static void r300SetStencilState(GLcontext * ctx, GLboolean state)
544 {
545 r300ContextPtr r300 = R300_CONTEXT(ctx);
546
547 if (r300->state.stencil.hw_stencil) {
548 R300_STATECHANGE(r300, zs);
549 if (state) {
550 r300->hw.zs.cmd[R300_ZS_CNTL_0] |=
551 R300_STENCIL_ENABLE;
552 } else {
553 r300->hw.zs.cmd[R300_ZS_CNTL_0] &=
554 ~R300_STENCIL_ENABLE;
555 }
556 } else {
557 #if R200_MERGED
558 FALLBACK(&r300->radeon, RADEON_FALLBACK_STENCIL, state);
559 #endif
560 }
561 }
562
563 static void r300UpdatePolygonMode(GLcontext * ctx)
564 {
565 r300ContextPtr r300 = R300_CONTEXT(ctx);
566 uint32_t hw_mode = R300_GA_POLY_MODE_DISABLE;
567
568 /* Only do something if a polygon mode is wanted, default is GL_FILL */
569 if (ctx->Polygon.FrontMode != GL_FILL ||
570 ctx->Polygon.BackMode != GL_FILL) {
571 GLenum f, b;
572
573 /* Handle GL_CW (clock wise and GL_CCW (counter clock wise)
574 * correctly by selecting the correct front and back face
575 */
576 if (ctx->Polygon.FrontFace == GL_CCW) {
577 f = ctx->Polygon.FrontMode;
578 b = ctx->Polygon.BackMode;
579 } else {
580 f = ctx->Polygon.BackMode;
581 b = ctx->Polygon.FrontMode;
582 }
583
584 /* Enable polygon mode */
585 hw_mode |= R300_GA_POLY_MODE_DUAL;
586
587 switch (f) {
588 case GL_LINE:
589 hw_mode |= R300_GA_POLY_MODE_FRONT_PTYPE_LINE;
590 break;
591 case GL_POINT:
592 hw_mode |= R300_GA_POLY_MODE_FRONT_PTYPE_POINT;
593 break;
594 case GL_FILL:
595 hw_mode |= R300_GA_POLY_MODE_FRONT_PTYPE_TRI;
596 break;
597 }
598
599 switch (b) {
600 case GL_LINE:
601 hw_mode |= R300_GA_POLY_MODE_BACK_PTYPE_LINE;
602 break;
603 case GL_POINT:
604 hw_mode |= R300_GA_POLY_MODE_BACK_PTYPE_POINT;
605 break;
606 case GL_FILL:
607 hw_mode |= R300_GA_POLY_MODE_BACK_PTYPE_TRI;
608 break;
609 }
610 }
611
612 if (r300->hw.polygon_mode.cmd[1] != hw_mode) {
613 R300_STATECHANGE(r300, polygon_mode);
614 r300->hw.polygon_mode.cmd[1] = hw_mode;
615 }
616
617 r300->hw.polygon_mode.cmd[2] = 0x00000001;
618 r300->hw.polygon_mode.cmd[3] = 0x00000000;
619 }
620
621 /**
622 * Change the culling mode.
623 *
624 * \note Mesa already filters redundant calls to this function.
625 */
626 static void r300CullFace(GLcontext * ctx, GLenum mode)
627 {
628 (void)mode;
629
630 r300UpdateCulling(ctx);
631 }
632
633 /**
634 * Change the polygon orientation.
635 *
636 * \note Mesa already filters redundant calls to this function.
637 */
638 static void r300FrontFace(GLcontext * ctx, GLenum mode)
639 {
640 (void)mode;
641
642 r300UpdateCulling(ctx);
643 r300UpdatePolygonMode(ctx);
644 }
645
646 /**
647 * Change the depth testing function.
648 *
649 * \note Mesa already filters redundant calls to this function.
650 */
651 static void r300DepthFunc(GLcontext * ctx, GLenum func)
652 {
653 (void)func;
654 r300SetDepthState(ctx);
655 }
656
657 /**
658 * Enable/Disable depth writing.
659 *
660 * \note Mesa already filters redundant calls to this function.
661 */
662 static void r300DepthMask(GLcontext * ctx, GLboolean mask)
663 {
664 (void)mask;
665 r300SetDepthState(ctx);
666 }
667
668 /**
669 * Handle glColorMask()
670 */
671 static void r300ColorMask(GLcontext * ctx,
672 GLboolean r, GLboolean g, GLboolean b, GLboolean a)
673 {
674 r300ContextPtr r300 = R300_CONTEXT(ctx);
675 int mask = (r ? RB3D_COLOR_CHANNEL_MASK_RED_MASK0 : 0) |
676 (g ? RB3D_COLOR_CHANNEL_MASK_GREEN_MASK0 : 0) |
677 (b ? RB3D_COLOR_CHANNEL_MASK_BLUE_MASK0 : 0) |
678 (a ? RB3D_COLOR_CHANNEL_MASK_ALPHA_MASK0 : 0);
679
680 if (mask != r300->hw.cmk.cmd[R300_CMK_COLORMASK]) {
681 R300_STATECHANGE(r300, cmk);
682 r300->hw.cmk.cmd[R300_CMK_COLORMASK] = mask;
683 }
684 }
685
686 /* =============================================================
687 * Fog
688 */
689 static void r300Fogfv(GLcontext * ctx, GLenum pname, const GLfloat * param)
690 {
691 r300ContextPtr r300 = R300_CONTEXT(ctx);
692 union {
693 int i;
694 float f;
695 } fogScale, fogStart;
696
697 (void)param;
698
699 fogScale.i = r300->hw.fogp.cmd[R300_FOGP_SCALE];
700 fogStart.i = r300->hw.fogp.cmd[R300_FOGP_START];
701
702 switch (pname) {
703 case GL_FOG_MODE:
704 if (!ctx->Fog.Enabled)
705 return;
706 switch (ctx->Fog.Mode) {
707 case GL_LINEAR:
708 R300_STATECHANGE(r300, fogs);
709 r300->hw.fogs.cmd[R300_FOGS_STATE] =
710 (r300->hw.fogs.
711 cmd[R300_FOGS_STATE] & ~R300_FG_FOG_BLEND_FN_MASK) |
712 R300_FG_FOG_BLEND_FN_LINEAR;
713
714 if (ctx->Fog.Start == ctx->Fog.End) {
715 fogScale.f = -1.0;
716 fogStart.f = 1.0;
717 } else {
718 fogScale.f =
719 1.0 / (ctx->Fog.End - ctx->Fog.Start);
720 fogStart.f =
721 -ctx->Fog.Start / (ctx->Fog.End -
722 ctx->Fog.Start);
723 }
724 break;
725 case GL_EXP:
726 R300_STATECHANGE(r300, fogs);
727 r300->hw.fogs.cmd[R300_FOGS_STATE] =
728 (r300->hw.fogs.
729 cmd[R300_FOGS_STATE] & ~R300_FG_FOG_BLEND_FN_MASK) |
730 R300_FG_FOG_BLEND_FN_EXP;
731 fogScale.f = 0.0933 * ctx->Fog.Density;
732 fogStart.f = 0.0;
733 break;
734 case GL_EXP2:
735 R300_STATECHANGE(r300, fogs);
736 r300->hw.fogs.cmd[R300_FOGS_STATE] =
737 (r300->hw.fogs.
738 cmd[R300_FOGS_STATE] & ~R300_FG_FOG_BLEND_FN_MASK) |
739 R300_FG_FOG_BLEND_FN_EXP2;
740 fogScale.f = 0.3 * ctx->Fog.Density;
741 fogStart.f = 0.0;
742 default:
743 return;
744 }
745 break;
746 case GL_FOG_DENSITY:
747 switch (ctx->Fog.Mode) {
748 case GL_EXP:
749 fogScale.f = 0.0933 * ctx->Fog.Density;
750 fogStart.f = 0.0;
751 break;
752 case GL_EXP2:
753 fogScale.f = 0.3 * ctx->Fog.Density;
754 fogStart.f = 0.0;
755 default:
756 break;
757 }
758 break;
759 case GL_FOG_START:
760 case GL_FOG_END:
761 if (ctx->Fog.Mode == GL_LINEAR) {
762 if (ctx->Fog.Start == ctx->Fog.End) {
763 fogScale.f = -1.0;
764 fogStart.f = 1.0;
765 } else {
766 fogScale.f =
767 1.0 / (ctx->Fog.End - ctx->Fog.Start);
768 fogStart.f =
769 -ctx->Fog.Start / (ctx->Fog.End -
770 ctx->Fog.Start);
771 }
772 }
773 break;
774 case GL_FOG_COLOR:
775 R300_STATECHANGE(r300, fogc);
776 r300->hw.fogc.cmd[R300_FOGC_R] =
777 (GLuint) (ctx->Fog.Color[0] * 1023.0F) & 0x3FF;
778 r300->hw.fogc.cmd[R300_FOGC_G] =
779 (GLuint) (ctx->Fog.Color[1] * 1023.0F) & 0x3FF;
780 r300->hw.fogc.cmd[R300_FOGC_B] =
781 (GLuint) (ctx->Fog.Color[2] * 1023.0F) & 0x3FF;
782 break;
783 case GL_FOG_COORD_SRC:
784 break;
785 default:
786 return;
787 }
788
789 if (fogScale.i != r300->hw.fogp.cmd[R300_FOGP_SCALE] ||
790 fogStart.i != r300->hw.fogp.cmd[R300_FOGP_START]) {
791 R300_STATECHANGE(r300, fogp);
792 r300->hw.fogp.cmd[R300_FOGP_SCALE] = fogScale.i;
793 r300->hw.fogp.cmd[R300_FOGP_START] = fogStart.i;
794 }
795 }
796
797 static void r300SetFogState(GLcontext * ctx, GLboolean state)
798 {
799 r300ContextPtr r300 = R300_CONTEXT(ctx);
800
801 R300_STATECHANGE(r300, fogs);
802 if (state) {
803 r300->hw.fogs.cmd[R300_FOGS_STATE] |= R300_FG_FOG_BLEND_ENABLE;
804
805 r300Fogfv(ctx, GL_FOG_MODE, NULL);
806 r300Fogfv(ctx, GL_FOG_DENSITY, &ctx->Fog.Density);
807 r300Fogfv(ctx, GL_FOG_START, &ctx->Fog.Start);
808 r300Fogfv(ctx, GL_FOG_END, &ctx->Fog.End);
809 r300Fogfv(ctx, GL_FOG_COLOR, ctx->Fog.Color);
810 } else {
811 r300->hw.fogs.cmd[R300_FOGS_STATE] &= ~R300_FG_FOG_BLEND_ENABLE;
812 }
813 }
814
815 /* =============================================================
816 * Point state
817 */
818 static void r300PointSize(GLcontext * ctx, GLfloat size)
819 {
820 r300ContextPtr r300 = R300_CONTEXT(ctx);
821 /* same size limits for AA, non-AA points */
822 size = CLAMP(size, ctx->Const.MinPointSize, ctx->Const.MaxPointSize);
823
824 R300_STATECHANGE(r300, ps);
825 r300->hw.ps.cmd[R300_PS_POINTSIZE] =
826 ((int)(size * 6) << R300_POINTSIZE_X_SHIFT) |
827 ((int)(size * 6) << R300_POINTSIZE_Y_SHIFT);
828 }
829
830 static void r300PointParameter(GLcontext * ctx, GLenum pname, const GLfloat * param)
831 {
832 r300ContextPtr r300 = R300_CONTEXT(ctx);
833
834 switch (pname) {
835 case GL_POINT_SIZE_MIN:
836 R300_STATECHANGE(r300, ga_point_minmax);
837 r300->hw.ga_point_minmax.cmd[1] &= ~R300_GA_POINT_MINMAX_MIN_MASK;
838 r300->hw.ga_point_minmax.cmd[1] |= (GLuint)(ctx->Point.MinSize * 16.0);
839 break;
840 case GL_POINT_SIZE_MAX:
841 R300_STATECHANGE(r300, ga_point_minmax);
842 r300->hw.ga_point_minmax.cmd[1] &= ~R300_GA_POINT_MINMAX_MAX_MASK;
843 r300->hw.ga_point_minmax.cmd[1] |= (GLuint)(ctx->Point.MaxSize * 16.0)
844 << R300_GA_POINT_MINMAX_MAX_SHIFT;
845 break;
846 case GL_POINT_DISTANCE_ATTENUATION:
847 break;
848 case GL_POINT_FADE_THRESHOLD_SIZE:
849 break;
850 default:
851 break;
852 }
853 }
854
855 /* =============================================================
856 * Line state
857 */
858 static void r300LineWidth(GLcontext * ctx, GLfloat widthf)
859 {
860 r300ContextPtr r300 = R300_CONTEXT(ctx);
861
862 widthf = CLAMP(widthf,
863 ctx->Const.MinPointSize,
864 ctx->Const.MaxPointSize);
865 R300_STATECHANGE(r300, lcntl);
866 r300->hw.lcntl.cmd[1] =
867 R300_LINE_CNT_HO | R300_LINE_CNT_VE | (int)(widthf * 6.0);
868 }
869
870 static void r300PolygonMode(GLcontext * ctx, GLenum face, GLenum mode)
871 {
872 (void)face;
873 (void)mode;
874
875 r300UpdatePolygonMode(ctx);
876 }
877
878 /* =============================================================
879 * Stencil
880 */
881
882 static int translate_stencil_op(int op)
883 {
884 switch (op) {
885 case GL_KEEP:
886 return R300_ZS_KEEP;
887 case GL_ZERO:
888 return R300_ZS_ZERO;
889 case GL_REPLACE:
890 return R300_ZS_REPLACE;
891 case GL_INCR:
892 return R300_ZS_INCR;
893 case GL_DECR:
894 return R300_ZS_DECR;
895 case GL_INCR_WRAP_EXT:
896 return R300_ZS_INCR_WRAP;
897 case GL_DECR_WRAP_EXT:
898 return R300_ZS_DECR_WRAP;
899 case GL_INVERT:
900 return R300_ZS_INVERT;
901 default:
902 WARN_ONCE("Do not know how to translate stencil op");
903 return R300_ZS_KEEP;
904 }
905 return 0;
906 }
907
908 static void r300ShadeModel(GLcontext * ctx, GLenum mode)
909 {
910 r300ContextPtr rmesa = R300_CONTEXT(ctx);
911
912 R300_STATECHANGE(rmesa, shade);
913 rmesa->hw.shade.cmd[1] = 0x00000002;
914 switch (mode) {
915 case GL_FLAT:
916 rmesa->hw.shade.cmd[2] = R300_RE_SHADE_MODEL_FLAT;
917 break;
918 case GL_SMOOTH:
919 rmesa->hw.shade.cmd[2] = R300_RE_SHADE_MODEL_SMOOTH;
920 break;
921 default:
922 return;
923 }
924 rmesa->hw.shade.cmd[3] = 0x00000000;
925 rmesa->hw.shade.cmd[4] = 0x00000000;
926 }
927
928 static void r300StencilFuncSeparate(GLcontext * ctx, GLenum face,
929 GLenum func, GLint ref, GLuint mask)
930 {
931 r300ContextPtr rmesa = R300_CONTEXT(ctx);
932 GLuint refmask =
933 (((ctx->Stencil.
934 Ref[0] & 0xff) << R300_STENCILREF_SHIFT) | ((ctx->
935 Stencil.
936 ValueMask
937 [0] &
938 0xff)
939 <<
940 R300_STENCILMASK_SHIFT));
941
942 GLuint flag;
943
944 R300_STATECHANGE(rmesa, zs);
945 rmesa->hw.zs.cmd[R300_ZS_CNTL_0] |= R300_STENCIL_FRONT_BACK;
946 rmesa->hw.zs.cmd[R300_ZS_CNTL_1] &= ~((R300_ZS_MASK <<
947 R300_S_FRONT_FUNC_SHIFT)
948 | (R300_ZS_MASK <<
949 R300_S_BACK_FUNC_SHIFT));
950
951 rmesa->hw.zs.cmd[R300_ZS_CNTL_2] &=
952 ~((R300_STENCILREF_MASK << R300_STENCILREF_SHIFT) |
953 (R300_STENCILREF_MASK << R300_STENCILMASK_SHIFT));
954
955 flag = translate_func(ctx->Stencil.Function[0]);
956 rmesa->hw.zs.cmd[R300_ZS_CNTL_1] |=
957 (flag << R300_S_FRONT_FUNC_SHIFT);
958
959 if (ctx->Stencil._TestTwoSide)
960 flag = translate_func(ctx->Stencil.Function[1]);
961
962 rmesa->hw.zs.cmd[R300_ZS_CNTL_1] |=
963 (flag << R300_S_BACK_FUNC_SHIFT);
964 rmesa->hw.zs.cmd[R300_ZS_CNTL_2] |= refmask;
965 }
966
967 static void r300StencilMaskSeparate(GLcontext * ctx, GLenum face, GLuint mask)
968 {
969 r300ContextPtr rmesa = R300_CONTEXT(ctx);
970
971 R300_STATECHANGE(rmesa, zs);
972 rmesa->hw.zs.cmd[R300_ZS_CNTL_2] &=
973 ~(R300_STENCILREF_MASK <<
974 R300_STENCILWRITEMASK_SHIFT);
975 rmesa->hw.zs.cmd[R300_ZS_CNTL_2] |=
976 (ctx->Stencil.
977 WriteMask[0] & R300_STENCILREF_MASK) <<
978 R300_STENCILWRITEMASK_SHIFT;
979 }
980
981 static void r300StencilOpSeparate(GLcontext * ctx, GLenum face,
982 GLenum fail, GLenum zfail, GLenum zpass)
983 {
984 r300ContextPtr rmesa = R300_CONTEXT(ctx);
985
986 R300_STATECHANGE(rmesa, zs);
987 /* It is easier to mask what's left.. */
988 rmesa->hw.zs.cmd[R300_ZS_CNTL_1] &=
989 (R300_ZS_MASK << R300_Z_FUNC_SHIFT) |
990 (R300_ZS_MASK << R300_S_FRONT_FUNC_SHIFT) |
991 (R300_ZS_MASK << R300_S_BACK_FUNC_SHIFT);
992
993 rmesa->hw.zs.cmd[R300_ZS_CNTL_1] |=
994 (translate_stencil_op(ctx->Stencil.FailFunc[0]) <<
995 R300_S_FRONT_SFAIL_OP_SHIFT)
996 | (translate_stencil_op(ctx->Stencil.ZFailFunc[0]) <<
997 R300_S_FRONT_ZFAIL_OP_SHIFT)
998 | (translate_stencil_op(ctx->Stencil.ZPassFunc[0]) <<
999 R300_S_FRONT_ZPASS_OP_SHIFT);
1000
1001 if (ctx->Stencil._TestTwoSide) {
1002 rmesa->hw.zs.cmd[R300_ZS_CNTL_1] |=
1003 (translate_stencil_op(ctx->Stencil.FailFunc[1]) <<
1004 R300_S_BACK_SFAIL_OP_SHIFT)
1005 | (translate_stencil_op(ctx->Stencil.ZFailFunc[1]) <<
1006 R300_S_BACK_ZFAIL_OP_SHIFT)
1007 | (translate_stencil_op(ctx->Stencil.ZPassFunc[1]) <<
1008 R300_S_BACK_ZPASS_OP_SHIFT);
1009 } else {
1010 rmesa->hw.zs.cmd[R300_ZS_CNTL_1] |=
1011 (translate_stencil_op(ctx->Stencil.FailFunc[0]) <<
1012 R300_S_BACK_SFAIL_OP_SHIFT)
1013 | (translate_stencil_op(ctx->Stencil.ZFailFunc[0]) <<
1014 R300_S_BACK_ZFAIL_OP_SHIFT)
1015 | (translate_stencil_op(ctx->Stencil.ZPassFunc[0]) <<
1016 R300_S_BACK_ZPASS_OP_SHIFT);
1017 }
1018 }
1019
1020 /* =============================================================
1021 * Window position and viewport transformation
1022 */
1023
1024 /*
1025 * To correctly position primitives:
1026 */
1027 #define SUBPIXEL_X 0.125
1028 #define SUBPIXEL_Y 0.125
1029
1030 static void r300UpdateWindow(GLcontext * ctx)
1031 {
1032 r300ContextPtr rmesa = R300_CONTEXT(ctx);
1033 __DRIdrawablePrivate *dPriv = rmesa->radeon.dri.drawable;
1034 GLfloat xoffset = dPriv ? (GLfloat) dPriv->x : 0;
1035 GLfloat yoffset = dPriv ? (GLfloat) dPriv->y + dPriv->h : 0;
1036 const GLfloat *v = ctx->Viewport._WindowMap.m;
1037
1038 GLfloat sx = v[MAT_SX];
1039 GLfloat tx = v[MAT_TX] + xoffset + SUBPIXEL_X;
1040 GLfloat sy = -v[MAT_SY];
1041 GLfloat ty = (-v[MAT_TY]) + yoffset + SUBPIXEL_Y;
1042 GLfloat sz = v[MAT_SZ] * rmesa->state.depth.scale;
1043 GLfloat tz = v[MAT_TZ] * rmesa->state.depth.scale;
1044
1045 R300_FIREVERTICES(rmesa);
1046 R300_STATECHANGE(rmesa, vpt);
1047
1048 rmesa->hw.vpt.cmd[R300_VPT_XSCALE] = r300PackFloat32(sx);
1049 rmesa->hw.vpt.cmd[R300_VPT_XOFFSET] = r300PackFloat32(tx);
1050 rmesa->hw.vpt.cmd[R300_VPT_YSCALE] = r300PackFloat32(sy);
1051 rmesa->hw.vpt.cmd[R300_VPT_YOFFSET] = r300PackFloat32(ty);
1052 rmesa->hw.vpt.cmd[R300_VPT_ZSCALE] = r300PackFloat32(sz);
1053 rmesa->hw.vpt.cmd[R300_VPT_ZOFFSET] = r300PackFloat32(tz);
1054 }
1055
1056 static void r300Viewport(GLcontext * ctx, GLint x, GLint y,
1057 GLsizei width, GLsizei height)
1058 {
1059 /* Don't pipeline viewport changes, conflict with window offset
1060 * setting below. Could apply deltas to rescue pipelined viewport
1061 * values, or keep the originals hanging around.
1062 */
1063 r300UpdateWindow(ctx);
1064 }
1065
1066 static void r300DepthRange(GLcontext * ctx, GLclampd nearval, GLclampd farval)
1067 {
1068 r300UpdateWindow(ctx);
1069 }
1070
1071 void r300UpdateViewportOffset(GLcontext * ctx)
1072 {
1073 r300ContextPtr rmesa = R300_CONTEXT(ctx);
1074 __DRIdrawablePrivate *dPriv = ((radeonContextPtr) rmesa)->dri.drawable;
1075 GLfloat xoffset = (GLfloat) dPriv->x;
1076 GLfloat yoffset = (GLfloat) dPriv->y + dPriv->h;
1077 const GLfloat *v = ctx->Viewport._WindowMap.m;
1078
1079 GLfloat tx = v[MAT_TX] + xoffset + SUBPIXEL_X;
1080 GLfloat ty = (-v[MAT_TY]) + yoffset + SUBPIXEL_Y;
1081
1082 if (rmesa->hw.vpt.cmd[R300_VPT_XOFFSET] != r300PackFloat32(tx) ||
1083 rmesa->hw.vpt.cmd[R300_VPT_YOFFSET] != r300PackFloat32(ty)) {
1084 /* Note: this should also modify whatever data the context reset
1085 * code uses...
1086 */
1087 R300_STATECHANGE(rmesa, vpt);
1088 rmesa->hw.vpt.cmd[R300_VPT_XOFFSET] = r300PackFloat32(tx);
1089 rmesa->hw.vpt.cmd[R300_VPT_YOFFSET] = r300PackFloat32(ty);
1090
1091 }
1092
1093 radeonUpdateScissor(ctx);
1094 }
1095
1096 /**
1097 * Tell the card where to render (offset, pitch).
1098 * Effected by glDrawBuffer, etc
1099 */
1100 void r300UpdateDrawBuffer(GLcontext * ctx)
1101 {
1102 r300ContextPtr rmesa = R300_CONTEXT(ctx);
1103 r300ContextPtr r300 = rmesa;
1104 struct gl_framebuffer *fb = ctx->DrawBuffer;
1105 driRenderbuffer *drb;
1106
1107 if (fb->_ColorDrawBufferIndexes[0] == BUFFER_FRONT_LEFT) {
1108 /* draw to front */
1109 drb =
1110 (driRenderbuffer *) fb->Attachment[BUFFER_FRONT_LEFT].
1111 Renderbuffer;
1112 } else if (fb->_ColorDrawBufferIndexes[0] == BUFFER_BACK_LEFT) {
1113 /* draw to back */
1114 drb =
1115 (driRenderbuffer *) fb->Attachment[BUFFER_BACK_LEFT].
1116 Renderbuffer;
1117 } else {
1118 /* drawing to multiple buffers, or none */
1119 return;
1120 }
1121
1122 assert(drb);
1123 assert(drb->flippedPitch);
1124
1125 R300_STATECHANGE(rmesa, cb);
1126
1127 r300->hw.cb.cmd[R300_CB_OFFSET] = drb->flippedOffset + //r300->radeon.state.color.drawOffset +
1128 r300->radeon.radeonScreen->fbLocation;
1129 r300->hw.cb.cmd[R300_CB_PITCH] = drb->flippedPitch; //r300->radeon.state.color.drawPitch;
1130
1131 if (r300->radeon.radeonScreen->cpp == 4)
1132 r300->hw.cb.cmd[R300_CB_PITCH] |= R300_COLOR_FORMAT_ARGB8888;
1133 else
1134 r300->hw.cb.cmd[R300_CB_PITCH] |= R300_COLOR_FORMAT_RGB565;
1135
1136 if (r300->radeon.sarea->tiling_enabled)
1137 r300->hw.cb.cmd[R300_CB_PITCH] |= R300_COLOR_TILE_ENABLE;
1138 #if 0
1139 R200_STATECHANGE(rmesa, ctx);
1140
1141 /* Note: we used the (possibly) page-flipped values */
1142 rmesa->hw.ctx.cmd[CTX_RB3D_COLOROFFSET]
1143 = ((drb->flippedOffset + rmesa->r200Screen->fbLocation)
1144 & R200_COLOROFFSET_MASK);
1145 rmesa->hw.ctx.cmd[CTX_RB3D_COLORPITCH] = drb->flippedPitch;
1146
1147 if (rmesa->sarea->tiling_enabled) {
1148 rmesa->hw.ctx.cmd[CTX_RB3D_COLORPITCH] |=
1149 R200_COLOR_TILE_ENABLE;
1150 }
1151 #endif
1152 }
1153
1154 static void
1155 r300FetchStateParameter(GLcontext * ctx,
1156 const gl_state_index state[STATE_LENGTH],
1157 GLfloat * value)
1158 {
1159 r300ContextPtr r300 = R300_CONTEXT(ctx);
1160
1161 switch (state[0]) {
1162 case STATE_INTERNAL:
1163 switch (state[1]) {
1164 case STATE_R300_WINDOW_DIMENSION:
1165 value[0] = r300->radeon.dri.drawable->w * 0.5f; /* width*0.5 */
1166 value[1] = r300->radeon.dri.drawable->h * 0.5f; /* height*0.5 */
1167 value[2] = 0.5F; /* for moving range [-1 1] -> [0 1] */
1168 value[3] = 1.0F; /* not used */
1169 break;
1170
1171 case STATE_R300_TEXRECT_FACTOR:{
1172 struct gl_texture_object *t =
1173 ctx->Texture.Unit[state[2]].CurrentRect;
1174
1175 if (t && t->Image[0][t->BaseLevel]) {
1176 struct gl_texture_image *image =
1177 t->Image[0][t->BaseLevel];
1178 value[0] = 1.0 / image->Width2;
1179 value[1] = 1.0 / image->Height2;
1180 } else {
1181 value[0] = 1.0;
1182 value[1] = 1.0;
1183 }
1184 value[2] = 1.0;
1185 value[3] = 1.0;
1186 break;
1187 }
1188
1189 default:
1190 break;
1191 }
1192 break;
1193
1194 default:
1195 break;
1196 }
1197 }
1198
1199 /**
1200 * Update R300's own internal state parameters.
1201 * For now just STATE_R300_WINDOW_DIMENSION
1202 */
1203 void r300UpdateStateParameters(GLcontext * ctx, GLuint new_state)
1204 {
1205 struct r300_fragment_program *fp;
1206 struct gl_program_parameter_list *paramList;
1207 GLuint i;
1208
1209 if (!(new_state & (_NEW_BUFFERS | _NEW_PROGRAM)))
1210 return;
1211
1212 fp = (struct r300_fragment_program *)ctx->FragmentProgram._Current;
1213 if (!fp)
1214 return;
1215
1216 paramList = fp->mesa_program.Base.Parameters;
1217
1218 if (!paramList)
1219 return;
1220
1221 for (i = 0; i < paramList->NumParameters; i++) {
1222 if (paramList->Parameters[i].Type == PROGRAM_STATE_VAR) {
1223 r300FetchStateParameter(ctx,
1224 paramList->Parameters[i].
1225 StateIndexes,
1226 paramList->ParameterValues[i]);
1227 }
1228 }
1229 }
1230
1231 /* =============================================================
1232 * Polygon state
1233 */
1234 static void r300PolygonOffset(GLcontext * ctx, GLfloat factor, GLfloat units)
1235 {
1236 r300ContextPtr rmesa = R300_CONTEXT(ctx);
1237 GLfloat constant = units;
1238
1239 switch (ctx->Visual.depthBits) {
1240 case 16:
1241 constant *= 4.0;
1242 break;
1243 case 24:
1244 constant *= 2.0;
1245 break;
1246 }
1247
1248 factor *= 12.0;
1249
1250 /* fprintf(stderr, "%s f:%f u:%f\n", __FUNCTION__, factor, constant); */
1251
1252 R300_STATECHANGE(rmesa, zbs);
1253 rmesa->hw.zbs.cmd[R300_ZBS_T_FACTOR] = r300PackFloat32(factor);
1254 rmesa->hw.zbs.cmd[R300_ZBS_T_CONSTANT] = r300PackFloat32(constant);
1255 rmesa->hw.zbs.cmd[R300_ZBS_W_FACTOR] = r300PackFloat32(factor);
1256 rmesa->hw.zbs.cmd[R300_ZBS_W_CONSTANT] = r300PackFloat32(constant);
1257 }
1258
1259 /* Routing and texture-related */
1260
1261 /* r300 doesnt handle GL_CLAMP and GL_MIRROR_CLAMP_EXT correctly when filter is NEAREST.
1262 * Since texwrap produces same results for GL_CLAMP and GL_CLAMP_TO_EDGE we use them instead.
1263 * We need to recalculate wrap modes whenever filter mode is changed because someone might do:
1264 * glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
1265 * glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
1266 * glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
1267 * Since r300 completely ignores R300_TX_CLAMP when either min or mag is nearest it cant handle
1268 * combinations where only one of them is nearest.
1269 */
1270 static unsigned long gen_fixed_filter(unsigned long f)
1271 {
1272 unsigned long mag, min, needs_fixing = 0;
1273 //return f;
1274
1275 /* We ignore MIRROR bit so we dont have to do everything twice */
1276 if ((f & ((7 - 1) << R300_TX_WRAP_S_SHIFT)) ==
1277 (R300_TX_CLAMP << R300_TX_WRAP_S_SHIFT)) {
1278 needs_fixing |= 1;
1279 }
1280 if ((f & ((7 - 1) << R300_TX_WRAP_T_SHIFT)) ==
1281 (R300_TX_CLAMP << R300_TX_WRAP_T_SHIFT)) {
1282 needs_fixing |= 2;
1283 }
1284 if ((f & ((7 - 1) << R300_TX_WRAP_R_SHIFT)) ==
1285 (R300_TX_CLAMP << R300_TX_WRAP_R_SHIFT)) {
1286 needs_fixing |= 4;
1287 }
1288
1289 if (!needs_fixing)
1290 return f;
1291
1292 mag = f & R300_TX_MAG_FILTER_MASK;
1293 min = f & (R300_TX_MIN_FILTER_MASK|R300_TX_MIN_FILTER_MIP_MASK);
1294
1295 /* TODO: Check for anisto filters too */
1296 if ((mag != R300_TX_MAG_FILTER_NEAREST)
1297 && (min != R300_TX_MIN_FILTER_NEAREST))
1298 return f;
1299
1300 /* r300 cant handle these modes hence we force nearest to linear */
1301 if ((mag == R300_TX_MAG_FILTER_NEAREST)
1302 && (min != R300_TX_MIN_FILTER_NEAREST)) {
1303 f &= ~R300_TX_MAG_FILTER_NEAREST;
1304 f |= R300_TX_MAG_FILTER_LINEAR;
1305 return f;
1306 }
1307
1308 if ((min == R300_TX_MIN_FILTER_NEAREST)
1309 && (mag != R300_TX_MAG_FILTER_NEAREST)) {
1310 f &= ~R300_TX_MIN_FILTER_NEAREST;
1311 f |= R300_TX_MIN_FILTER_LINEAR;
1312 return f;
1313 }
1314
1315 /* Both are nearest */
1316 if (needs_fixing & 1) {
1317 f &= ~((7 - 1) << R300_TX_WRAP_S_SHIFT);
1318 f |= R300_TX_CLAMP_TO_EDGE << R300_TX_WRAP_S_SHIFT;
1319 }
1320 if (needs_fixing & 2) {
1321 f &= ~((7 - 1) << R300_TX_WRAP_T_SHIFT);
1322 f |= R300_TX_CLAMP_TO_EDGE << R300_TX_WRAP_T_SHIFT;
1323 }
1324 if (needs_fixing & 4) {
1325 f &= ~((7 - 1) << R300_TX_WRAP_R_SHIFT);
1326 f |= R300_TX_CLAMP_TO_EDGE << R300_TX_WRAP_R_SHIFT;
1327 }
1328 return f;
1329 }
1330
1331 static void r300SetupFragmentShaderTextures(GLcontext *ctx, int *tmu_mappings)
1332 {
1333 r300ContextPtr r300 = R300_CONTEXT(ctx);
1334 int i;
1335 struct r300_fragment_program *fp = (struct r300_fragment_program *)
1336 (char *)ctx->FragmentProgram._Current;
1337 struct r300_fragment_program_code *code = &fp->code;
1338
1339 R300_STATECHANGE(r300, fpt);
1340
1341 for (i = 0; i < code->tex.length; i++) {
1342 int unit;
1343 int opcode;
1344 unsigned long val;
1345
1346 unit = code->tex.inst[i] >> R300_TEX_ID_SHIFT;
1347 unit &= 15;
1348
1349 val = code->tex.inst[i];
1350 val &= ~R300_TEX_ID_MASK;
1351
1352 opcode =
1353 (val & R300_TEX_INST_MASK) >> R300_TEX_INST_SHIFT;
1354 if (opcode == R300_TEX_OP_KIL) {
1355 r300->hw.fpt.cmd[R300_FPT_INSTR_0 + i] = val;
1356 } else {
1357 if (tmu_mappings[unit] >= 0) {
1358 val |=
1359 tmu_mappings[unit] <<
1360 R300_TEX_ID_SHIFT;
1361 r300->hw.fpt.cmd[R300_FPT_INSTR_0 + i] = val;
1362 } else {
1363 // We get here when the corresponding texture image is incomplete
1364 // (e.g. incomplete mipmaps etc.)
1365 r300->hw.fpt.cmd[R300_FPT_INSTR_0 + i] = val;
1366 }
1367 }
1368 }
1369
1370 r300->hw.fpt.cmd[R300_FPT_CMD_0] =
1371 cmdpacket0(R300_US_TEX_INST_0, code->tex.length);
1372 }
1373
1374 static void r500SetupFragmentShaderTextures(GLcontext *ctx, int *tmu_mappings)
1375 {
1376 int i;
1377 struct r500_fragment_program *fp = (struct r500_fragment_program *)
1378 (char *)ctx->FragmentProgram._Current;
1379 struct r500_fragment_program_code *code = &fp->code;
1380
1381 /* find all the texture instructions and relocate the texture units */
1382 for (i = 0; i < code->inst_end + 1; i++) {
1383 if ((code->inst[i].inst0 & 0x3) == R500_INST_TYPE_TEX) {
1384 uint32_t val;
1385 int unit, opcode, new_unit;
1386
1387 val = code->inst[i].inst1;
1388
1389 unit = (val >> 16) & 0xf;
1390
1391 val &= ~(0xf << 16);
1392
1393 opcode = val & (0x7 << 22);
1394 if (opcode == R500_TEX_INST_TEXKILL) {
1395 new_unit = 0;
1396 } else {
1397 if (tmu_mappings[unit] >= 0) {
1398 new_unit = tmu_mappings[unit];
1399 } else {
1400 new_unit = 0;
1401 }
1402 }
1403 val |= R500_TEX_ID(new_unit);
1404 code->inst[i].inst1 = val;
1405 }
1406 }
1407 }
1408
1409 static GLuint translate_lod_bias(GLfloat bias)
1410 {
1411 GLint b = (int)(bias*32);
1412 if (b >= (1 << 9))
1413 b = (1 << 9)-1;
1414 else if (b < -(1 << 9))
1415 b = -(1 << 9);
1416 return (((GLuint)b) << R300_LOD_BIAS_SHIFT) & R300_LOD_BIAS_MASK;
1417 }
1418
1419 static void r300SetupTextures(GLcontext * ctx)
1420 {
1421 int i, mtu;
1422 struct r300_tex_obj *t;
1423 r300ContextPtr r300 = R300_CONTEXT(ctx);
1424 int hw_tmu = 0;
1425 int last_hw_tmu = -1; /* -1 translates into no setup costs for fields */
1426 int tmu_mappings[R300_MAX_TEXTURE_UNITS] = { -1, };
1427 struct r300_fragment_program *fp = (struct r300_fragment_program *)
1428 (char *)ctx->FragmentProgram._Current;
1429
1430 R300_STATECHANGE(r300, txe);
1431 R300_STATECHANGE(r300, tex.filter);
1432 R300_STATECHANGE(r300, tex.filter_1);
1433 R300_STATECHANGE(r300, tex.size);
1434 R300_STATECHANGE(r300, tex.format);
1435 R300_STATECHANGE(r300, tex.pitch);
1436 R300_STATECHANGE(r300, tex.offset);
1437 R300_STATECHANGE(r300, tex.chroma_key);
1438 R300_STATECHANGE(r300, tex.border_color);
1439
1440 r300->hw.txe.cmd[R300_TXE_ENABLE] = 0x0;
1441
1442 mtu = r300->radeon.glCtx->Const.MaxTextureUnits;
1443 if (RADEON_DEBUG & DEBUG_STATE)
1444 fprintf(stderr, "mtu=%d\n", mtu);
1445
1446 if (mtu > R300_MAX_TEXTURE_UNITS) {
1447 fprintf(stderr,
1448 "Aiiee ! mtu=%d is greater than R300_MAX_TEXTURE_UNITS=%d\n",
1449 mtu, R300_MAX_TEXTURE_UNITS);
1450 _mesa_exit(-1);
1451 }
1452
1453 /* We cannot let disabled tmu offsets pass DRM */
1454 for (i = 0; i < mtu; i++) {
1455 if (ctx->Texture.Unit[i]._ReallyEnabled) {
1456
1457 #if 0 /* Enables old behaviour */
1458 hw_tmu = i;
1459 #endif
1460 tmu_mappings[i] = hw_tmu;
1461
1462 t = r300->state.texture.unit[i].texobj;
1463 /* XXX questionable fix for bug 9170: */
1464 if (!t)
1465 continue;
1466
1467 if ((t->format & 0xffffff00) == 0xffffff00) {
1468 WARN_ONCE
1469 ("unknown texture format (entry %x) encountered. Help me !\n",
1470 t->format & 0xff);
1471 }
1472
1473 if (RADEON_DEBUG & DEBUG_STATE)
1474 fprintf(stderr,
1475 "Activating texture unit %d\n", i);
1476
1477 r300->hw.txe.cmd[R300_TXE_ENABLE] |= (1 << hw_tmu);
1478
1479 r300->hw.tex.filter.cmd[R300_TEX_VALUE_0 +
1480 hw_tmu] =
1481 gen_fixed_filter(t->filter) | (hw_tmu << 28);
1482 /* Note: There is a LOD bias per texture unit and a LOD bias
1483 * per texture object. We add them here to get the correct behaviour.
1484 * (The per-texture object LOD bias was introduced in OpenGL 1.4
1485 * and is not present in the EXT_texture_object extension).
1486 */
1487 r300->hw.tex.filter_1.cmd[R300_TEX_VALUE_0 + hw_tmu] =
1488 t->filter_1 |
1489 translate_lod_bias(ctx->Texture.Unit[i].LodBias + t->base.tObj->LodBias);
1490 r300->hw.tex.size.cmd[R300_TEX_VALUE_0 + hw_tmu] =
1491 t->size;
1492 r300->hw.tex.format.cmd[R300_TEX_VALUE_0 +
1493 hw_tmu] = t->format;
1494 r300->hw.tex.pitch.cmd[R300_TEX_VALUE_0 + hw_tmu] =
1495 t->pitch_reg;
1496 r300->hw.tex.offset.cmd[R300_TEX_VALUE_0 +
1497 hw_tmu] = t->offset;
1498
1499 if (t->offset & R300_TXO_MACRO_TILE) {
1500 WARN_ONCE("macro tiling enabled!\n");
1501 }
1502
1503 if (t->offset & R300_TXO_MICRO_TILE) {
1504 WARN_ONCE("micro tiling enabled!\n");
1505 }
1506
1507 r300->hw.tex.chroma_key.cmd[R300_TEX_VALUE_0 +
1508 hw_tmu] = 0x0;
1509 r300->hw.tex.border_color.cmd[R300_TEX_VALUE_0 +
1510 hw_tmu] =
1511 t->pp_border_color;
1512
1513 last_hw_tmu = hw_tmu;
1514
1515 hw_tmu++;
1516 }
1517 }
1518
1519 r300->hw.tex.filter.cmd[R300_TEX_CMD_0] =
1520 cmdpacket0(R300_TX_FILTER0_0, last_hw_tmu + 1);
1521 r300->hw.tex.filter_1.cmd[R300_TEX_CMD_0] =
1522 cmdpacket0(R300_TX_FILTER1_0, last_hw_tmu + 1);
1523 r300->hw.tex.size.cmd[R300_TEX_CMD_0] =
1524 cmdpacket0(R300_TX_SIZE_0, last_hw_tmu + 1);
1525 r300->hw.tex.format.cmd[R300_TEX_CMD_0] =
1526 cmdpacket0(R300_TX_FORMAT_0, last_hw_tmu + 1);
1527 r300->hw.tex.pitch.cmd[R300_TEX_CMD_0] =
1528 cmdpacket0(R300_TX_FORMAT2_0, last_hw_tmu + 1);
1529 r300->hw.tex.offset.cmd[R300_TEX_CMD_0] =
1530 cmdpacket0(R300_TX_OFFSET_0, last_hw_tmu + 1);
1531 r300->hw.tex.chroma_key.cmd[R300_TEX_CMD_0] =
1532 cmdpacket0(R300_TX_CHROMA_KEY_0, last_hw_tmu + 1);
1533 r300->hw.tex.border_color.cmd[R300_TEX_CMD_0] =
1534 cmdpacket0(R300_TX_BORDER_COLOR_0, last_hw_tmu + 1);
1535
1536 if (!fp) /* should only happenen once, just after context is created */
1537 return;
1538
1539 if (r300->radeon.radeonScreen->chip_family < CHIP_FAMILY_RV515) {
1540 if (fp->mesa_program.UsesKill && last_hw_tmu < 0) {
1541 // The KILL operation requires the first texture unit
1542 // to be enabled.
1543 r300->hw.txe.cmd[R300_TXE_ENABLE] |= 1;
1544 r300->hw.tex.filter.cmd[R300_TEX_VALUE_0] = 0;
1545 r300->hw.tex.filter.cmd[R300_TEX_CMD_0] =
1546 cmdpacket0(R300_TX_FILTER0_0, 1);
1547 }
1548 r300SetupFragmentShaderTextures(ctx, tmu_mappings);
1549 } else
1550 r500SetupFragmentShaderTextures(ctx, tmu_mappings);
1551
1552 if (RADEON_DEBUG & DEBUG_STATE)
1553 fprintf(stderr, "TX_ENABLE: %08x last_hw_tmu=%d\n",
1554 r300->hw.txe.cmd[R300_TXE_ENABLE], last_hw_tmu);
1555 }
1556
1557 union r300_outputs_written {
1558 GLuint vp_outputs; /* hw_tcl_on */
1559 DECLARE_RENDERINPUTS(index_bitset); /* !hw_tcl_on */
1560 };
1561
1562 #define R300_OUTPUTS_WRITTEN_TEST(ow, vp_result, tnl_attrib) \
1563 ((hw_tcl_on) ? (ow).vp_outputs & (1 << (vp_result)) : \
1564 RENDERINPUTS_TEST( (ow.index_bitset), (tnl_attrib) ))
1565
1566 static void r300SetupRSUnit(GLcontext * ctx)
1567 {
1568 r300ContextPtr r300 = R300_CONTEXT(ctx);
1569 /* I'm still unsure if these are needed */
1570 GLuint interp_col[8];
1571 TNLcontext *tnl = TNL_CONTEXT(ctx);
1572 struct vertex_buffer *VB = &tnl->vb;
1573 union r300_outputs_written OutputsWritten;
1574 GLuint InputsRead;
1575 int fp_reg, high_rr;
1576 int col_interp_nr;
1577 int rs_tex_count = 0, rs_col_count = 0;
1578 int i, count;
1579
1580 memset(interp_col, 0, sizeof(interp_col));
1581
1582 if (hw_tcl_on)
1583 OutputsWritten.vp_outputs = CURRENT_VERTEX_SHADER(ctx)->key.OutputsWritten;
1584 else
1585 RENDERINPUTS_COPY(OutputsWritten.index_bitset, r300->state.render_inputs_bitset);
1586
1587 if (ctx->FragmentProgram._Current)
1588 InputsRead = ctx->FragmentProgram._Current->Base.InputsRead;
1589 else {
1590 fprintf(stderr, "No ctx->FragmentProgram._Current!!\n");
1591 return; /* This should only ever happen once.. */
1592 }
1593
1594 R300_STATECHANGE(r300, ri);
1595 R300_STATECHANGE(r300, rc);
1596 R300_STATECHANGE(r300, rr);
1597
1598 fp_reg = col_interp_nr = high_rr = 0;
1599
1600 r300->hw.rr.cmd[R300_RR_INST_1] = 0;
1601
1602 if (InputsRead & FRAG_BIT_WPOS) {
1603 for (i = 0; i < ctx->Const.MaxTextureUnits; i++)
1604 if (!(InputsRead & (FRAG_BIT_TEX0 << i)))
1605 break;
1606
1607 if (i == ctx->Const.MaxTextureUnits) {
1608 fprintf(stderr, "\tno free texcoord found...\n");
1609 _mesa_exit(-1);
1610 }
1611
1612 InputsRead |= (FRAG_BIT_TEX0 << i);
1613 InputsRead &= ~FRAG_BIT_WPOS;
1614 }
1615
1616 if (InputsRead & FRAG_BIT_COL0) {
1617 count = VB->AttribPtr[_TNL_ATTRIB_COLOR0]->size;
1618 interp_col[0] |= R300_RS_COL_PTR(rs_col_count);
1619 if (count == 3)
1620 interp_col[0] |= R300_RS_COL_FMT(R300_RS_COL_FMT_RGB1);
1621 rs_col_count += count;
1622 }
1623 else
1624 interp_col[0] = R300_RS_COL_FMT(R300_RS_COL_FMT_0001);
1625
1626 if (InputsRead & FRAG_BIT_COL1) {
1627 count = VB->AttribPtr[_TNL_ATTRIB_COLOR1]->size;
1628 if (count == 3)
1629 interp_col[1] |= R300_RS_COL_FMT(R300_RS_COL_FMT_RGB0);
1630 interp_col[1] |= R300_RS_COL_PTR(1);
1631 rs_col_count += count;
1632 }
1633
1634
1635 for (i = 0; i < ctx->Const.MaxTextureUnits; i++) {
1636 int swiz;
1637
1638 /* with TCL we always seem to route 4 components */
1639 if (hw_tcl_on)
1640 count = 4;
1641 else
1642 count = VB->AttribPtr[_TNL_ATTRIB_TEX(i)]->size;
1643
1644 r300->hw.ri.cmd[R300_RI_INTERP_0 + i] = interp_col[i] | rs_tex_count;
1645 switch(count) {
1646 case 4: swiz = R300_RS_SEL_S(0) | R300_RS_SEL_T(1) | R300_RS_SEL_R(2) | R300_RS_SEL_Q(3); break;
1647 case 3: swiz = R300_RS_SEL_S(0) | R300_RS_SEL_T(1) | R300_RS_SEL_R(2) | R300_RS_SEL_Q(R300_RS_SEL_K1); break;
1648 default:
1649 case 1:
1650 case 2: swiz = R300_RS_SEL_S(0) | R300_RS_SEL_T(1) | R300_RS_SEL_R(R300_RS_SEL_K0) | R300_RS_SEL_Q(R300_RS_SEL_K1); break;
1651 };
1652
1653 r300->hw.ri.cmd[R300_RI_INTERP_0 + i] |= swiz;
1654
1655 r300->hw.rr.cmd[R300_RR_INST_0 + fp_reg] = 0;
1656 if (InputsRead & (FRAG_BIT_TEX0 << i)) {
1657
1658 rs_tex_count += count;
1659
1660 //assert(r300->state.texture.tc_count != 0);
1661 r300->hw.rr.cmd[R300_RR_INST_0 + fp_reg] |= R300_RS_INST_TEX_CN_WRITE | i /* source INTERP */
1662 | (fp_reg << R300_RS_INST_TEX_ADDR_SHIFT);
1663 high_rr = fp_reg;
1664
1665 /* Passing invalid data here can lock the GPU. */
1666 if (R300_OUTPUTS_WRITTEN_TEST(OutputsWritten, VERT_RESULT_TEX0 + i, _TNL_ATTRIB_TEX(i))) {
1667 InputsRead &= ~(FRAG_BIT_TEX0 << i);
1668 fp_reg++;
1669 } else {
1670 WARN_ONCE("fragprog wants coords for tex%d, vp doesn't provide them!\n", i);
1671 }
1672 }
1673 }
1674
1675 if (InputsRead & FRAG_BIT_COL0) {
1676 if (R300_OUTPUTS_WRITTEN_TEST(OutputsWritten, VERT_RESULT_COL0, _TNL_ATTRIB_COLOR0)) {
1677 r300->hw.rr.cmd[R300_RR_INST_0] |= R300_RS_INST_COL_ID(0) | R300_RS_INST_COL_CN_WRITE | (fp_reg++ << R300_RS_INST_COL_ADDR_SHIFT);
1678 InputsRead &= ~FRAG_BIT_COL0;
1679 col_interp_nr++;
1680 } else {
1681 WARN_ONCE("fragprog wants col0, vp doesn't provide it\n");
1682 }
1683 }
1684
1685 if (InputsRead & FRAG_BIT_COL1) {
1686 if (R300_OUTPUTS_WRITTEN_TEST(OutputsWritten, VERT_RESULT_COL1, _TNL_ATTRIB_COLOR1)) {
1687 r300->hw.rr.cmd[R300_RR_INST_1] |= R300_RS_INST_COL_ID(1) | R300_RS_INST_COL_CN_WRITE | (fp_reg++ << R300_RS_INST_COL_ADDR_SHIFT);
1688 InputsRead &= ~FRAG_BIT_COL1;
1689 if (high_rr < 1)
1690 high_rr = 1;
1691 col_interp_nr++;
1692 } else {
1693 WARN_ONCE("fragprog wants col1, vp doesn't provide it\n");
1694 }
1695 }
1696
1697 /* Need at least one. This might still lock as the values are undefined... */
1698 if (rs_tex_count == 0 && col_interp_nr == 0) {
1699 r300->hw.rr.cmd[R300_RR_INST_0] |= R300_RS_INST_COL_ID(0) | R300_RS_INST_COL_CN_WRITE | (fp_reg++ << R300_RS_INST_COL_ADDR_SHIFT);
1700 col_interp_nr++;
1701 }
1702
1703 r300->hw.rc.cmd[1] = 0 | (rs_tex_count << R300_IT_COUNT_SHIFT)
1704 | (col_interp_nr << R300_IC_COUNT_SHIFT)
1705 | R300_HIRES_EN;
1706
1707 assert(high_rr >= 0);
1708 r300->hw.rr.cmd[R300_RR_CMD_0] = cmdpacket0(R300_RS_INST_0, high_rr + 1);
1709 r300->hw.rc.cmd[2] = high_rr;
1710
1711 if (InputsRead)
1712 WARN_ONCE("Don't know how to satisfy InputsRead=0x%08x\n", InputsRead);
1713 }
1714
1715 static void r500SetupRSUnit(GLcontext * ctx)
1716 {
1717 r300ContextPtr r300 = R300_CONTEXT(ctx);
1718 /* I'm still unsure if these are needed */
1719 GLuint interp_col[8];
1720 union r300_outputs_written OutputsWritten;
1721 TNLcontext *tnl = TNL_CONTEXT(ctx);
1722 struct vertex_buffer *VB = &tnl->vb;
1723 GLuint InputsRead;
1724 int fp_reg, high_rr;
1725 int rs_col_count = 0;
1726 int in_texcoords, col_interp_nr;
1727 int i, count;
1728
1729 memset(interp_col, 0, sizeof(interp_col));
1730 if (hw_tcl_on)
1731 OutputsWritten.vp_outputs = CURRENT_VERTEX_SHADER(ctx)->key.OutputsWritten;
1732 else
1733 RENDERINPUTS_COPY(OutputsWritten.index_bitset, r300->state.render_inputs_bitset);
1734
1735 if (ctx->FragmentProgram._Current)
1736 InputsRead = ctx->FragmentProgram._Current->Base.InputsRead;
1737 else {
1738 fprintf(stderr, "No ctx->FragmentProgram._Current!!\n");
1739 return; /* This should only ever happen once.. */
1740 }
1741
1742 R300_STATECHANGE(r300, ri);
1743 R300_STATECHANGE(r300, rc);
1744 R300_STATECHANGE(r300, rr);
1745
1746 fp_reg = col_interp_nr = high_rr = in_texcoords = 0;
1747
1748 r300->hw.rr.cmd[R300_RR_INST_1] = 0;
1749
1750 if (InputsRead & FRAG_BIT_WPOS) {
1751 for (i = 0; i < ctx->Const.MaxTextureUnits; i++)
1752 if (!(InputsRead & (FRAG_BIT_TEX0 << i)))
1753 break;
1754
1755 if (i == ctx->Const.MaxTextureUnits) {
1756 fprintf(stderr, "\tno free texcoord found...\n");
1757 _mesa_exit(-1);
1758 }
1759
1760 InputsRead |= (FRAG_BIT_TEX0 << i);
1761 InputsRead &= ~FRAG_BIT_WPOS;
1762 }
1763
1764 if (InputsRead & FRAG_BIT_COL0) {
1765 count = VB->AttribPtr[_TNL_ATTRIB_COLOR0]->size;
1766 interp_col[0] |= R500_RS_COL_PTR(rs_col_count);
1767 if (count == 3)
1768 interp_col[0] |= R500_RS_COL_FMT(R300_RS_COL_FMT_RGB1);
1769 rs_col_count += count;
1770 }
1771 else
1772 interp_col[0] = R500_RS_COL_FMT(R300_RS_COL_FMT_0001);
1773
1774 if (InputsRead & FRAG_BIT_COL1) {
1775 count = VB->AttribPtr[_TNL_ATTRIB_COLOR1]->size;
1776 interp_col[1] |= R500_RS_COL_PTR(1);
1777 if (count == 3)
1778 interp_col[1] |= R500_RS_COL_FMT(R300_RS_COL_FMT_RGB0);
1779 rs_col_count += count;
1780 }
1781
1782 for (i = 0; i < ctx->Const.MaxTextureUnits; i++) {
1783 GLuint swiz = 0;
1784
1785 /* with TCL we always seem to route 4 components */
1786 if (InputsRead & (FRAG_BIT_TEX0 << i)) {
1787
1788 if (hw_tcl_on)
1789 count = 4;
1790 else
1791 count = VB->AttribPtr[_TNL_ATTRIB_TEX(i)]->size;
1792
1793 /* always have on texcoord */
1794 swiz |= in_texcoords++ << R500_RS_IP_TEX_PTR_S_SHIFT;
1795 if (count >= 2)
1796 swiz |= in_texcoords++ << R500_RS_IP_TEX_PTR_T_SHIFT;
1797 else
1798 swiz |= R500_RS_IP_PTR_K0 << R500_RS_IP_TEX_PTR_T_SHIFT;
1799
1800 if (count >= 3)
1801 swiz |= in_texcoords++ << R500_RS_IP_TEX_PTR_R_SHIFT;
1802 else
1803 swiz |= R500_RS_IP_PTR_K0 << R500_RS_IP_TEX_PTR_R_SHIFT;
1804
1805 if (count == 4)
1806 swiz |= in_texcoords++ << R500_RS_IP_TEX_PTR_Q_SHIFT;
1807 else
1808 swiz |= R500_RS_IP_PTR_K1 << R500_RS_IP_TEX_PTR_Q_SHIFT;
1809
1810 } else
1811 swiz = (R500_RS_IP_PTR_K0 << R500_RS_IP_TEX_PTR_S_SHIFT) |
1812 (R500_RS_IP_PTR_K0 << R500_RS_IP_TEX_PTR_T_SHIFT) |
1813 (R500_RS_IP_PTR_K0 << R500_RS_IP_TEX_PTR_R_SHIFT) |
1814 (R500_RS_IP_PTR_K1 << R500_RS_IP_TEX_PTR_Q_SHIFT);
1815
1816 r300->hw.ri.cmd[R300_RI_INTERP_0 + i] = interp_col[i] | swiz;
1817
1818 r300->hw.rr.cmd[R300_RR_INST_0 + fp_reg] = 0;
1819 if (InputsRead & (FRAG_BIT_TEX0 << i)) {
1820 //assert(r300->state.texture.tc_count != 0);
1821 r300->hw.rr.cmd[R300_RR_INST_0 + fp_reg] |= R500_RS_INST_TEX_CN_WRITE | i /* source INTERP */
1822 | (fp_reg << R500_RS_INST_TEX_ADDR_SHIFT);
1823 high_rr = fp_reg;
1824
1825 /* Passing invalid data here can lock the GPU. */
1826 if (R300_OUTPUTS_WRITTEN_TEST(OutputsWritten, VERT_RESULT_TEX0 + i, _TNL_ATTRIB_TEX(i))) {
1827 InputsRead &= ~(FRAG_BIT_TEX0 << i);
1828 fp_reg++;
1829 } else {
1830 WARN_ONCE("fragprog wants coords for tex%d, vp doesn't provide them!\n", i);
1831 }
1832 }
1833 }
1834
1835 if (InputsRead & FRAG_BIT_COL0) {
1836 if (R300_OUTPUTS_WRITTEN_TEST(OutputsWritten, VERT_RESULT_COL0, _TNL_ATTRIB_COLOR0)) {
1837 r300->hw.rr.cmd[R300_RR_INST_0] |= R500_RS_INST_COL_CN_WRITE | (fp_reg++ << R500_RS_INST_COL_ADDR_SHIFT);
1838 InputsRead &= ~FRAG_BIT_COL0;
1839 col_interp_nr++;
1840 } else {
1841 WARN_ONCE("fragprog wants col0, vp doesn't provide it\n");
1842 }
1843 }
1844
1845 if (InputsRead & FRAG_BIT_COL1) {
1846 if (R300_OUTPUTS_WRITTEN_TEST(OutputsWritten, VERT_RESULT_COL1, _TNL_ATTRIB_COLOR1)) {
1847 r300->hw.rr.cmd[R300_RR_INST_1] |= (1 << 12) | R500_RS_INST_COL_CN_WRITE | (fp_reg++ << R500_RS_INST_COL_ADDR_SHIFT);
1848 InputsRead &= ~FRAG_BIT_COL1;
1849 if (high_rr < 1)
1850 high_rr = 1;
1851 col_interp_nr++;
1852 } else {
1853 WARN_ONCE("fragprog wants col1, vp doesn't provide it\n");
1854 }
1855 }
1856
1857 /* Need at least one. This might still lock as the values are undefined... */
1858 if (in_texcoords == 0 && col_interp_nr == 0) {
1859 r300->hw.rr.cmd[R300_RR_INST_0] |= 0 | R500_RS_INST_COL_CN_WRITE | (fp_reg++ << R500_RS_INST_COL_ADDR_SHIFT);
1860 col_interp_nr++;
1861 }
1862
1863 r300->hw.rc.cmd[1] = 0 | (in_texcoords << R300_IT_COUNT_SHIFT)
1864 | (col_interp_nr << R300_IC_COUNT_SHIFT)
1865 | R300_HIRES_EN;
1866
1867 assert(high_rr >= 0);
1868 r300->hw.rr.cmd[R300_RR_CMD_0] = cmdpacket0(R500_RS_INST_0, high_rr + 1);
1869 r300->hw.rc.cmd[2] = 0xC0 | high_rr;
1870
1871 if (InputsRead)
1872 WARN_ONCE("Don't know how to satisfy InputsRead=0x%08x\n", InputsRead);
1873 }
1874
1875
1876
1877
1878 #define bump_vpu_count(ptr, new_count) do{\
1879 drm_r300_cmd_header_t* _p=((drm_r300_cmd_header_t*)(ptr));\
1880 int _nc=(new_count)/4; \
1881 assert(_nc < 256); \
1882 if(_nc>_p->vpu.count)_p->vpu.count=_nc;\
1883 }while(0)
1884
1885 static INLINE void r300SetupVertexProgramFragment(r300ContextPtr r300, int dest, struct r300_vertex_shader_fragment *vsf)
1886 {
1887 int i;
1888
1889 if (vsf->length == 0)
1890 return;
1891
1892 if (vsf->length & 0x3) {
1893 fprintf(stderr, "VERTEX_SHADER_FRAGMENT must have length divisible by 4\n");
1894 _mesa_exit(-1);
1895 }
1896
1897 switch ((dest >> 8) & 0xf) {
1898 case 0:
1899 R300_STATECHANGE(r300, vpi);
1900 for (i = 0; i < vsf->length; i++)
1901 r300->hw.vpi.cmd[R300_VPI_INSTR_0 + i + 4 * (dest & 0xff)] = (vsf->body.d[i]);
1902 bump_vpu_count(r300->hw.vpi.cmd, vsf->length + 4 * (dest & 0xff));
1903 break;
1904
1905 case 2:
1906 R300_STATECHANGE(r300, vpp);
1907 for (i = 0; i < vsf->length; i++)
1908 r300->hw.vpp.cmd[R300_VPP_PARAM_0 + i + 4 * (dest & 0xff)] = (vsf->body.d[i]);
1909 bump_vpu_count(r300->hw.vpp.cmd, vsf->length + 4 * (dest & 0xff));
1910 break;
1911 case 4:
1912 R300_STATECHANGE(r300, vps);
1913 for (i = 0; i < vsf->length; i++)
1914 r300->hw.vps.cmd[1 + i + 4 * (dest & 0xff)] = (vsf->body.d[i]);
1915 bump_vpu_count(r300->hw.vps.cmd, vsf->length + 4 * (dest & 0xff));
1916 break;
1917 default:
1918 fprintf(stderr, "%s:%s don't know how to handle dest %04x\n", __FILE__, __FUNCTION__, dest);
1919 _mesa_exit(-1);
1920 }
1921 }
1922
1923 #define MIN3(a, b, c) ((a) < (b) ? MIN2(a, c) : MIN2(b, c))
1924
1925
1926 static void r300VapCntl(r300ContextPtr rmesa, GLuint input_count,
1927 GLuint output_count, GLuint temp_count)
1928 {
1929 int vtx_mem_size;
1930 int pvs_num_slots;
1931 int pvs_num_cntrls;
1932
1933 /* Flush PVS engine before changing PVS_NUM_SLOTS, PVS_NUM_CNTRLS.
1934 * See r500 docs 6.5.2 - done in emit */
1935
1936 /* avoid division by zero */
1937 if (input_count == 0) input_count = 1;
1938 if (output_count == 0) output_count = 1;
1939 if (temp_count == 0) temp_count = 1;
1940
1941 if (rmesa->radeon.radeonScreen->chip_family >= CHIP_FAMILY_RV515)
1942 vtx_mem_size = 128;
1943 else
1944 vtx_mem_size = 72;
1945
1946 pvs_num_slots = MIN3(10, vtx_mem_size/input_count, vtx_mem_size/output_count);
1947 pvs_num_cntrls = MIN2(6, vtx_mem_size/temp_count);
1948
1949 R300_STATECHANGE(rmesa, vap_cntl);
1950 if (rmesa->radeon.radeonScreen->chip_flags & RADEON_CHIPSET_TCL) {
1951 rmesa->hw.vap_cntl.cmd[R300_VAP_CNTL_INSTR] =
1952 (pvs_num_slots << R300_PVS_NUM_SLOTS_SHIFT) |
1953 (pvs_num_cntrls << R300_PVS_NUM_CNTLRS_SHIFT) |
1954 (12 << R300_VF_MAX_VTX_NUM_SHIFT);
1955 if (rmesa->radeon.radeonScreen->chip_family >= CHIP_FAMILY_RV515)
1956 rmesa->hw.vap_cntl.cmd[R300_VAP_CNTL_INSTR] |= R500_TCL_STATE_OPTIMIZATION;
1957 } else
1958 /* not sure about non-tcl */
1959 rmesa->hw.vap_cntl.cmd[R300_VAP_CNTL_INSTR] = ((10 << R300_PVS_NUM_SLOTS_SHIFT) |
1960 (5 << R300_PVS_NUM_CNTLRS_SHIFT) |
1961 (5 << R300_VF_MAX_VTX_NUM_SHIFT));
1962
1963 if (rmesa->radeon.radeonScreen->chip_family == CHIP_FAMILY_RV515)
1964 rmesa->hw.vap_cntl.cmd[R300_VAP_CNTL_INSTR] |= (2 << R300_PVS_NUM_FPUS_SHIFT);
1965 else if ((rmesa->radeon.radeonScreen->chip_family == CHIP_FAMILY_RV530) ||
1966 (rmesa->radeon.radeonScreen->chip_family == CHIP_FAMILY_RV560))
1967 rmesa->hw.vap_cntl.cmd[R300_VAP_CNTL_INSTR] |= (5 << R300_PVS_NUM_FPUS_SHIFT);
1968 else if (rmesa->radeon.radeonScreen->chip_family == CHIP_FAMILY_R420)
1969 rmesa->hw.vap_cntl.cmd[R300_VAP_CNTL_INSTR] |= (6 << R300_PVS_NUM_FPUS_SHIFT);
1970 else if ((rmesa->radeon.radeonScreen->chip_family == CHIP_FAMILY_R520) ||
1971 (rmesa->radeon.radeonScreen->chip_family == CHIP_FAMILY_R580) ||
1972 (rmesa->radeon.radeonScreen->chip_family == CHIP_FAMILY_RV570))
1973 rmesa->hw.vap_cntl.cmd[R300_VAP_CNTL_INSTR] |= (8 << R300_PVS_NUM_FPUS_SHIFT);
1974 else
1975 rmesa->hw.vap_cntl.cmd[R300_VAP_CNTL_INSTR] |= (4 << R300_PVS_NUM_FPUS_SHIFT);
1976
1977 }
1978
1979 static void r300SetupDefaultVertexProgram(r300ContextPtr rmesa)
1980 {
1981 struct r300_vertex_shader_state *prog = &(rmesa->state.vertex_shader);
1982 GLuint o_reg = 0;
1983 GLuint i_reg = 0;
1984 int i;
1985 int inst_count = 0;
1986 int param_count = 0;
1987 int program_end = 0;
1988
1989 for (i = VERT_ATTRIB_POS; i < VERT_ATTRIB_MAX; i++) {
1990 if (rmesa->state.sw_tcl_inputs[i] != -1) {
1991 prog->program.body.i[program_end + 0] = PVS_OP_DST_OPERAND(VE_MULTIPLY, GL_FALSE, GL_FALSE, o_reg++, VSF_FLAG_ALL, PVS_DST_REG_OUT);
1992 prog->program.body.i[program_end + 1] = PVS_SRC_OPERAND(rmesa->state.sw_tcl_inputs[i], PVS_SRC_SELECT_X, PVS_SRC_SELECT_Y, PVS_SRC_SELECT_Z, PVS_SRC_SELECT_W, PVS_SRC_REG_INPUT, VSF_FLAG_NONE);
1993 prog->program.body.i[program_end + 2] = PVS_SRC_OPERAND(rmesa->state.sw_tcl_inputs[i], PVS_SRC_SELECT_FORCE_1, PVS_SRC_SELECT_FORCE_1, PVS_SRC_SELECT_FORCE_1, PVS_SRC_SELECT_FORCE_1, PVS_SRC_REG_INPUT, VSF_FLAG_NONE);
1994 prog->program.body.i[program_end + 3] = PVS_SRC_OPERAND(rmesa->state.sw_tcl_inputs[i], PVS_SRC_SELECT_FORCE_1, PVS_SRC_SELECT_FORCE_1, PVS_SRC_SELECT_FORCE_1, PVS_SRC_SELECT_FORCE_1, PVS_SRC_REG_INPUT, VSF_FLAG_NONE);
1995 program_end += 4;
1996 i_reg++;
1997 }
1998 }
1999
2000 prog->program.length = program_end;
2001
2002 r300SetupVertexProgramFragment(rmesa, R300_PVS_CODE_START,
2003 &(prog->program));
2004 inst_count = (prog->program.length / 4) - 1;
2005
2006 r300VapCntl(rmesa, i_reg, o_reg, 0);
2007
2008 R300_STATECHANGE(rmesa, pvs);
2009 rmesa->hw.pvs.cmd[R300_PVS_CNTL_1] =
2010 (0 << R300_PVS_FIRST_INST_SHIFT) |
2011 (inst_count << R300_PVS_XYZW_VALID_INST_SHIFT) |
2012 (inst_count << R300_PVS_LAST_INST_SHIFT);
2013 rmesa->hw.pvs.cmd[R300_PVS_CNTL_2] =
2014 (0 << R300_PVS_CONST_BASE_OFFSET_SHIFT) |
2015 (param_count << R300_PVS_MAX_CONST_ADDR_SHIFT);
2016 rmesa->hw.pvs.cmd[R300_PVS_CNTL_3] =
2017 (inst_count << R300_PVS_LAST_VTX_SRC_INST_SHIFT);
2018 }
2019
2020 static int bit_count (int x)
2021 {
2022 x = ((x & 0xaaaaaaaaU) >> 1) + (x & 0x55555555U);
2023 x = ((x & 0xccccccccU) >> 2) + (x & 0x33333333U);
2024 x = (x >> 16) + (x & 0xffff);
2025 x = ((x & 0xf0f0) >> 4) + (x & 0x0f0f);
2026 return (x >> 8) + (x & 0x00ff);
2027 }
2028
2029 static void r300SetupRealVertexProgram(r300ContextPtr rmesa)
2030 {
2031 GLcontext *ctx = rmesa->radeon.glCtx;
2032 struct r300_vertex_program *prog = (struct r300_vertex_program *)CURRENT_VERTEX_SHADER(ctx);
2033 int inst_count = 0;
2034 int param_count = 0;
2035
2036 /* FIXME: r300SetupVertexProgramFragment */
2037 R300_STATECHANGE(rmesa, vpp);
2038 param_count =
2039 r300VertexProgUpdateParams(ctx,
2040 (struct r300_vertex_program_cont *)
2041 ctx->VertexProgram._Current,
2042 (float *)&rmesa->hw.vpp.
2043 cmd[R300_VPP_PARAM_0]);
2044 bump_vpu_count(rmesa->hw.vpp.cmd, param_count);
2045 param_count /= 4;
2046
2047 r300SetupVertexProgramFragment(rmesa, R300_PVS_CODE_START, &(prog->program));
2048 inst_count = (prog->program.length / 4) - 1;
2049
2050 r300VapCntl(rmesa, bit_count(prog->key.InputsRead),
2051 bit_count(prog->key.OutputsWritten), prog->num_temporaries);
2052
2053 R300_STATECHANGE(rmesa, pvs);
2054 rmesa->hw.pvs.cmd[R300_PVS_CNTL_1] =
2055 (0 << R300_PVS_FIRST_INST_SHIFT) |
2056 (inst_count << R300_PVS_XYZW_VALID_INST_SHIFT) |
2057 (inst_count << R300_PVS_LAST_INST_SHIFT);
2058 rmesa->hw.pvs.cmd[R300_PVS_CNTL_2] =
2059 (0 << R300_PVS_CONST_BASE_OFFSET_SHIFT) |
2060 (param_count << R300_PVS_MAX_CONST_ADDR_SHIFT);
2061 rmesa->hw.pvs.cmd[R300_PVS_CNTL_3] =
2062 (inst_count << R300_PVS_LAST_VTX_SRC_INST_SHIFT);
2063 }
2064
2065 static void r300SetupVertexProgram(r300ContextPtr rmesa)
2066 {
2067 GLcontext *ctx = rmesa->radeon.glCtx;
2068
2069 /* Reset state, in case we don't use something */
2070 ((drm_r300_cmd_header_t *) rmesa->hw.vpp.cmd)->vpu.count = 0;
2071 ((drm_r300_cmd_header_t *) rmesa->hw.vpi.cmd)->vpu.count = 0;
2072 ((drm_r300_cmd_header_t *) rmesa->hw.vps.cmd)->vpu.count = 0;
2073
2074 /* Not sure why this doesnt work...
2075 0x400 area might have something to do with pixel shaders as it appears right after pfs programming.
2076 0x406 is set to { 0.0, 0.0, 1.0, 0.0 } most of the time but should change with smooth points and in other rare cases. */
2077 //setup_vertex_shader_fragment(rmesa, 0x406, &unk4);
2078 if (hw_tcl_on && ((struct r300_vertex_program *)CURRENT_VERTEX_SHADER(ctx))->translated) {
2079 r300SetupRealVertexProgram(rmesa);
2080 } else {
2081 /* FIXME: This needs to be replaced by vertex shader generation code. */
2082 r300SetupDefaultVertexProgram(rmesa);
2083 }
2084
2085 }
2086
2087 /**
2088 * Enable/Disable states.
2089 *
2090 * \note Mesa already filters redundant calls to this function.
2091 */
2092 static void r300Enable(GLcontext * ctx, GLenum cap, GLboolean state)
2093 {
2094 if (RADEON_DEBUG & DEBUG_STATE)
2095 fprintf(stderr, "%s( %s = %s )\n", __FUNCTION__,
2096 _mesa_lookup_enum_by_nr(cap),
2097 state ? "GL_TRUE" : "GL_FALSE");
2098
2099 switch (cap) {
2100 case GL_TEXTURE_1D:
2101 case GL_TEXTURE_2D:
2102 case GL_TEXTURE_3D:
2103 /* empty */
2104 break;
2105 case GL_FOG:
2106 r300SetFogState(ctx, state);
2107 break;
2108 case GL_ALPHA_TEST:
2109 r300SetAlphaState(ctx);
2110 break;
2111 case GL_BLEND:
2112 case GL_COLOR_LOGIC_OP:
2113 r300SetBlendState(ctx);
2114 break;
2115 case GL_CLIP_PLANE0:
2116 case GL_CLIP_PLANE1:
2117 case GL_CLIP_PLANE2:
2118 case GL_CLIP_PLANE3:
2119 case GL_CLIP_PLANE4:
2120 case GL_CLIP_PLANE5:
2121 r300SetClipPlaneState(ctx, cap, state);
2122 break;
2123 case GL_DEPTH_TEST:
2124 r300SetDepthState(ctx);
2125 break;
2126 case GL_STENCIL_TEST:
2127 r300SetStencilState(ctx, state);
2128 break;
2129 case GL_CULL_FACE:
2130 r300UpdateCulling(ctx);
2131 break;
2132 case GL_POLYGON_OFFSET_POINT:
2133 case GL_POLYGON_OFFSET_LINE:
2134 case GL_POLYGON_OFFSET_FILL:
2135 r300SetPolygonOffsetState(ctx, state);
2136 break;
2137 default:
2138 radeonEnable(ctx, cap, state);
2139 break;
2140 }
2141 }
2142
2143 /**
2144 * Completely recalculates hardware state based on the Mesa state.
2145 */
2146 static void r300ResetHwState(r300ContextPtr r300)
2147 {
2148 GLcontext *ctx = r300->radeon.glCtx;
2149 int has_tcl = 1;
2150
2151 if (!(r300->radeon.radeonScreen->chip_flags & RADEON_CHIPSET_TCL))
2152 has_tcl = 0;
2153
2154 if (RADEON_DEBUG & DEBUG_STATE)
2155 fprintf(stderr, "%s\n", __FUNCTION__);
2156
2157 r300UpdateWindow(ctx);
2158
2159 r300ColorMask(ctx,
2160 ctx->Color.ColorMask[RCOMP],
2161 ctx->Color.ColorMask[GCOMP],
2162 ctx->Color.ColorMask[BCOMP], ctx->Color.ColorMask[ACOMP]);
2163
2164 r300Enable(ctx, GL_DEPTH_TEST, ctx->Depth.Test);
2165 r300DepthMask(ctx, ctx->Depth.Mask);
2166 r300DepthFunc(ctx, ctx->Depth.Func);
2167
2168 /* stencil */
2169 r300Enable(ctx, GL_STENCIL_TEST, ctx->Stencil.Enabled);
2170 r300StencilMaskSeparate(ctx, 0, ctx->Stencil.WriteMask[0]);
2171 r300StencilFuncSeparate(ctx, 0, ctx->Stencil.Function[0],
2172 ctx->Stencil.Ref[0], ctx->Stencil.ValueMask[0]);
2173 r300StencilOpSeparate(ctx, 0, ctx->Stencil.FailFunc[0],
2174 ctx->Stencil.ZFailFunc[0],
2175 ctx->Stencil.ZPassFunc[0]);
2176
2177 r300UpdateCulling(ctx);
2178
2179 r300UpdateTextureState(ctx);
2180
2181 r300SetBlendState(ctx);
2182
2183 r300AlphaFunc(ctx, ctx->Color.AlphaFunc, ctx->Color.AlphaRef);
2184 r300Enable(ctx, GL_ALPHA_TEST, ctx->Color.AlphaEnabled);
2185
2186 r300->hw.vte.cmd[1] = R300_VPORT_X_SCALE_ENA
2187 | R300_VPORT_X_OFFSET_ENA
2188 | R300_VPORT_Y_SCALE_ENA
2189 | R300_VPORT_Y_OFFSET_ENA
2190 | R300_VPORT_Z_SCALE_ENA
2191 | R300_VPORT_Z_OFFSET_ENA | R300_VTX_W0_FMT;
2192 r300->hw.vte.cmd[2] = 0x00000008;
2193
2194 r300->hw.vap_vf_max_vtx_indx.cmd[1] = 0x00FFFFFF;
2195 r300->hw.vap_vf_max_vtx_indx.cmd[2] = 0x00000000;
2196
2197 #ifdef MESA_LITTLE_ENDIAN
2198 r300->hw.vap_cntl_status.cmd[1] = R300_VC_NO_SWAP;
2199 #else
2200 r300->hw.vap_cntl_status.cmd[1] = R300_VC_32BIT_SWAP;
2201 #endif
2202
2203 /* disable VAP/TCL on non-TCL capable chips */
2204 if (!has_tcl)
2205 r300->hw.vap_cntl_status.cmd[1] |= R300_VAP_TCL_BYPASS;
2206
2207 r300->hw.vap_psc_sgn_norm_cntl.cmd[1] = 0xAAAAAAAA;
2208
2209 /* XXX: Other families? */
2210 if (has_tcl) {
2211 r300->hw.vap_clip_cntl.cmd[1] = R300_PS_UCP_MODE_DIST_COP;
2212
2213 r300->hw.vap_clip.cmd[1] = r300PackFloat32(1.0); /* X */
2214 r300->hw.vap_clip.cmd[2] = r300PackFloat32(1.0); /* X */
2215 r300->hw.vap_clip.cmd[3] = r300PackFloat32(1.0); /* Y */
2216 r300->hw.vap_clip.cmd[4] = r300PackFloat32(1.0); /* Y */
2217
2218 switch (r300->radeon.radeonScreen->chip_family) {
2219 case CHIP_FAMILY_R300:
2220 r300->hw.vap_pvs_vtx_timeout_reg.cmd[1] = R300_2288_R300;
2221 break;
2222 default:
2223 r300->hw.vap_pvs_vtx_timeout_reg.cmd[1] = R300_2288_RV350;
2224 break;
2225 }
2226 }
2227
2228 r300->hw.gb_enable.cmd[1] = R300_GB_POINT_STUFF_ENABLE
2229 | R300_GB_LINE_STUFF_ENABLE
2230 | R300_GB_TRIANGLE_STUFF_ENABLE;
2231
2232 r300->hw.gb_misc.cmd[R300_GB_MISC_MSPOS_0] = 0x66666666;
2233 r300->hw.gb_misc.cmd[R300_GB_MISC_MSPOS_1] = 0x06666666;
2234
2235 r300->hw.gb_misc.cmd[R300_GB_MISC_TILE_CONFIG] =
2236 R300_GB_TILE_ENABLE | R300_GB_TILE_SIZE_16 /*| R300_GB_SUBPIXEL_1_16*/;
2237 switch (r300->radeon.radeonScreen->num_gb_pipes) {
2238 case 1:
2239 default:
2240 r300->hw.gb_misc.cmd[R300_GB_MISC_TILE_CONFIG] |=
2241 R300_GB_TILE_PIPE_COUNT_RV300;
2242 break;
2243 case 2:
2244 r300->hw.gb_misc.cmd[R300_GB_MISC_TILE_CONFIG] |=
2245 R300_GB_TILE_PIPE_COUNT_R300;
2246 break;
2247 case 3:
2248 r300->hw.gb_misc.cmd[R300_GB_MISC_TILE_CONFIG] |=
2249 R300_GB_TILE_PIPE_COUNT_R420_3P;
2250 break;
2251 case 4:
2252 r300->hw.gb_misc.cmd[R300_GB_MISC_TILE_CONFIG] |=
2253 R300_GB_TILE_PIPE_COUNT_R420;
2254 break;
2255 }
2256
2257 /* XXX: set to 0 when fog is disabled? */
2258 r300->hw.gb_misc.cmd[R300_GB_MISC_SELECT] = R300_GB_FOG_SELECT_1_1_W;
2259
2260 /* XXX: Enable anti-aliasing? */
2261 r300->hw.gb_misc.cmd[R300_GB_MISC_AA_CONFIG] = GB_AA_CONFIG_AA_DISABLE;
2262
2263 r300->hw.ga_point_s0.cmd[1] = r300PackFloat32(0.0);
2264 r300->hw.ga_point_s0.cmd[2] = r300PackFloat32(0.0);
2265 r300->hw.ga_point_s0.cmd[3] = r300PackFloat32(1.0);
2266 r300->hw.ga_point_s0.cmd[4] = r300PackFloat32(1.0);
2267
2268 r300->hw.ga_triangle_stipple.cmd[1] = 0x00050005;
2269
2270 r300PointSize(ctx, 1.0);
2271
2272 r300->hw.ga_point_minmax.cmd[1] = 0x18000006;
2273 r300->hw.ga_point_minmax.cmd[2] = 0x00020006;
2274 r300->hw.ga_point_minmax.cmd[3] = r300PackFloat32(1.0 / 192.0);
2275
2276 r300LineWidth(ctx, 1.0);
2277
2278 r300->hw.ga_line_stipple.cmd[1] = 0;
2279 r300->hw.ga_line_stipple.cmd[2] = r300PackFloat32(0.0);
2280 r300->hw.ga_line_stipple.cmd[3] = r300PackFloat32(1.0);
2281
2282 r300ShadeModel(ctx, ctx->Light.ShadeModel);
2283
2284 r300PolygonMode(ctx, GL_FRONT, ctx->Polygon.FrontMode);
2285 r300PolygonMode(ctx, GL_BACK, ctx->Polygon.BackMode);
2286 r300->hw.zbias_cntl.cmd[1] = 0x00000000;
2287
2288 r300PolygonOffset(ctx, ctx->Polygon.OffsetFactor,
2289 ctx->Polygon.OffsetUnits);
2290 r300Enable(ctx, GL_POLYGON_OFFSET_POINT, ctx->Polygon.OffsetPoint);
2291 r300Enable(ctx, GL_POLYGON_OFFSET_LINE, ctx->Polygon.OffsetLine);
2292 r300Enable(ctx, GL_POLYGON_OFFSET_FILL, ctx->Polygon.OffsetFill);
2293
2294 r300->hw.su_depth_scale.cmd[1] = 0x4B7FFFFF;
2295 r300->hw.su_depth_scale.cmd[2] = 0x00000000;
2296
2297 r300->hw.sc_hyperz.cmd[1] = 0x0000001C;
2298 r300->hw.sc_hyperz.cmd[2] = 0x2DA49525;
2299
2300 r300->hw.sc_screendoor.cmd[1] = 0x00FFFFFF;
2301
2302 r300->hw.us_out_fmt.cmd[1] = R500_OUT_FMT_C4_8 |
2303 R500_C0_SEL_B | R500_C1_SEL_G | R500_C2_SEL_R | R500_C3_SEL_A;
2304 r300->hw.us_out_fmt.cmd[2] = R500_OUT_FMT_UNUSED |
2305 R500_C0_SEL_B | R500_C1_SEL_G | R500_C2_SEL_R | R500_C3_SEL_A;
2306 r300->hw.us_out_fmt.cmd[3] = R500_OUT_FMT_UNUSED |
2307 R500_C0_SEL_B | R500_C1_SEL_G | R500_C2_SEL_R | R500_C3_SEL_A;
2308 r300->hw.us_out_fmt.cmd[4] = R500_OUT_FMT_UNUSED |
2309 R500_C0_SEL_B | R500_C1_SEL_G | R500_C2_SEL_R | R500_C3_SEL_A;
2310 r300->hw.us_out_fmt.cmd[5] = R300_W_FMT_W24;
2311
2312 r300Enable(ctx, GL_FOG, ctx->Fog.Enabled);
2313 r300Fogfv(ctx, GL_FOG_MODE, NULL);
2314 r300Fogfv(ctx, GL_FOG_DENSITY, &ctx->Fog.Density);
2315 r300Fogfv(ctx, GL_FOG_START, &ctx->Fog.Start);
2316 r300Fogfv(ctx, GL_FOG_END, &ctx->Fog.End);
2317 r300Fogfv(ctx, GL_FOG_COLOR, ctx->Fog.Color);
2318 r300Fogfv(ctx, GL_FOG_COORDINATE_SOURCE_EXT, NULL);
2319
2320 r300->hw.fg_depth_src.cmd[1] = 0;
2321
2322 r300->hw.rb3d_cctl.cmd[1] = 0;
2323
2324 r300BlendColor(ctx, ctx->Color.BlendColor);
2325
2326 /* Again, r300ClearBuffer uses this */
2327 r300->hw.cb.cmd[R300_CB_OFFSET] =
2328 r300->radeon.state.color.drawOffset +
2329 r300->radeon.radeonScreen->fbLocation;
2330 r300->hw.cb.cmd[R300_CB_PITCH] = r300->radeon.state.color.drawPitch;
2331
2332 if (r300->radeon.radeonScreen->cpp == 4)
2333 r300->hw.cb.cmd[R300_CB_PITCH] |= R300_COLOR_FORMAT_ARGB8888;
2334 else
2335 r300->hw.cb.cmd[R300_CB_PITCH] |= R300_COLOR_FORMAT_RGB565;
2336
2337 if (r300->radeon.sarea->tiling_enabled)
2338 r300->hw.cb.cmd[R300_CB_PITCH] |= R300_COLOR_TILE_ENABLE;
2339
2340 r300->hw.rb3d_dither_ctl.cmd[1] = 0;
2341 r300->hw.rb3d_dither_ctl.cmd[2] = 0;
2342 r300->hw.rb3d_dither_ctl.cmd[3] = 0;
2343 r300->hw.rb3d_dither_ctl.cmd[4] = 0;
2344 r300->hw.rb3d_dither_ctl.cmd[5] = 0;
2345 r300->hw.rb3d_dither_ctl.cmd[6] = 0;
2346 r300->hw.rb3d_dither_ctl.cmd[7] = 0;
2347 r300->hw.rb3d_dither_ctl.cmd[8] = 0;
2348 r300->hw.rb3d_dither_ctl.cmd[9] = 0;
2349
2350 r300->hw.rb3d_aaresolve_ctl.cmd[1] = 0;
2351
2352 r300->hw.rb3d_discard_src_pixel_lte_threshold.cmd[1] = 0x00000000;
2353 r300->hw.rb3d_discard_src_pixel_lte_threshold.cmd[2] = 0xffffffff;
2354
2355 r300->hw.zb.cmd[R300_ZB_OFFSET] =
2356 r300->radeon.radeonScreen->depthOffset +
2357 r300->radeon.radeonScreen->fbLocation;
2358 r300->hw.zb.cmd[R300_ZB_PITCH] = r300->radeon.radeonScreen->depthPitch;
2359
2360 if (r300->radeon.sarea->tiling_enabled) {
2361 /* XXX: Turn off when clearing buffers ? */
2362 r300->hw.zb.cmd[R300_ZB_PITCH] |= R300_DEPTHMACROTILE_ENABLE;
2363
2364 if (ctx->Visual.depthBits == 24)
2365 r300->hw.zb.cmd[R300_ZB_PITCH] |=
2366 R300_DEPTHMICROTILE_TILED;
2367 }
2368
2369 r300->hw.zb_depthclearvalue.cmd[1] = 0;
2370
2371 switch (ctx->Visual.depthBits) {
2372 case 16:
2373 r300->hw.zstencil_format.cmd[1] = R300_DEPTHFORMAT_16BIT_INT_Z;
2374 break;
2375 case 24:
2376 r300->hw.zstencil_format.cmd[1] = R300_DEPTHFORMAT_24BIT_INT_Z_8BIT_STENCIL;
2377 break;
2378 default:
2379 fprintf(stderr, "Error: Unsupported depth %d... exiting\n", ctx->Visual.depthBits);
2380 _mesa_exit(-1);
2381 }
2382
2383 r300->hw.zstencil_format.cmd[2] = R300_ZTOP_DISABLE;
2384 r300->hw.zstencil_format.cmd[3] = 0x00000003;
2385 r300->hw.zstencil_format.cmd[4] = 0x00000000;
2386 r300SetEarlyZState(ctx);
2387
2388 r300->hw.unk4F30.cmd[1] = 0;
2389 r300->hw.unk4F30.cmd[2] = 0;
2390
2391 r300->hw.zb_hiz_offset.cmd[1] = 0;
2392
2393 r300->hw.zb_hiz_pitch.cmd[1] = 0;
2394
2395 r300VapCntl(r300, 0, 0, 0);
2396 if (has_tcl) {
2397 r300->hw.vps.cmd[R300_VPS_ZERO_0] = 0;
2398 r300->hw.vps.cmd[R300_VPS_ZERO_1] = 0;
2399 r300->hw.vps.cmd[R300_VPS_POINTSIZE] = r300PackFloat32(1.0);
2400 r300->hw.vps.cmd[R300_VPS_ZERO_3] = 0;
2401 }
2402
2403 r300->hw.all_dirty = GL_TRUE;
2404 }
2405
2406 void r300UpdateShaders(r300ContextPtr rmesa)
2407 {
2408 GLcontext *ctx;
2409 struct r300_vertex_program *vp;
2410 int i;
2411
2412 ctx = rmesa->radeon.glCtx;
2413
2414 if (rmesa->NewGLState && hw_tcl_on) {
2415 rmesa->NewGLState = 0;
2416
2417 for (i = _TNL_FIRST_MAT; i <= _TNL_LAST_MAT; i++) {
2418 rmesa->temp_attrib[i] =
2419 TNL_CONTEXT(ctx)->vb.AttribPtr[i];
2420 TNL_CONTEXT(ctx)->vb.AttribPtr[i] =
2421 &rmesa->dummy_attrib[i];
2422 }
2423
2424 _tnl_UpdateFixedFunctionProgram(ctx);
2425
2426 for (i = _TNL_FIRST_MAT; i <= _TNL_LAST_MAT; i++) {
2427 TNL_CONTEXT(ctx)->vb.AttribPtr[i] =
2428 rmesa->temp_attrib[i];
2429 }
2430
2431 r300SelectVertexShader(rmesa);
2432 vp = (struct r300_vertex_program *)
2433 CURRENT_VERTEX_SHADER(ctx);
2434 /*if (vp->translated == GL_FALSE)
2435 r300TranslateVertexShader(vp); */
2436 if (vp->translated == GL_FALSE) {
2437 fprintf(stderr, "Failing back to sw-tcl\n");
2438 hw_tcl_on = future_hw_tcl_on = 0;
2439 r300ResetHwState(rmesa);
2440
2441 r300UpdateStateParameters(ctx, _NEW_PROGRAM);
2442 return;
2443 }
2444 }
2445 r300UpdateStateParameters(ctx, _NEW_PROGRAM);
2446 }
2447
2448 static void r300SetupPixelShader(r300ContextPtr rmesa)
2449 {
2450 GLcontext *ctx = rmesa->radeon.glCtx;
2451 struct r300_fragment_program *fp = (struct r300_fragment_program *)
2452 (char *)ctx->FragmentProgram._Current;
2453 struct r300_fragment_program_code *code;
2454 int i, k;
2455
2456 if (!fp) /* should only happenen once, just after context is created */
2457 return;
2458
2459 r300TranslateFragmentShader(rmesa, fp);
2460 if (!fp->translated) {
2461 fprintf(stderr, "%s: No valid fragment shader, exiting\n",
2462 __FUNCTION__);
2463 return;
2464 }
2465 code = &fp->code;
2466
2467 r300SetupTextures(ctx);
2468
2469 R300_STATECHANGE(rmesa, fpi[0]);
2470 rmesa->hw.fpi[0].cmd[R300_FPI_CMD_0] = cmdpacket0(R300_US_ALU_RGB_INST_0, code->alu_end + 1);
2471 for (i = 0; i <= code->alu_end; i++) {
2472 rmesa->hw.fpi[0].cmd[R300_FPI_INSTR_0 + i] = code->alu.inst[i].inst0;
2473 }
2474
2475 R300_STATECHANGE(rmesa, fpi[1]);
2476 rmesa->hw.fpi[1].cmd[R300_FPI_CMD_0] = cmdpacket0(R300_US_ALU_RGB_ADDR_0, code->alu_end + 1);
2477 for (i = 0; i <= code->alu_end; i++) {
2478 rmesa->hw.fpi[1].cmd[R300_FPI_INSTR_0 + i] = code->alu.inst[i].inst1;
2479 }
2480
2481 R300_STATECHANGE(rmesa, fpi[2]);
2482 rmesa->hw.fpi[2].cmd[R300_FPI_CMD_0] = cmdpacket0(R300_US_ALU_ALPHA_INST_0, code->alu_end + 1);
2483 for (i = 0; i <= code->alu_end; i++) {
2484 rmesa->hw.fpi[2].cmd[R300_FPI_INSTR_0 + i] = code->alu.inst[i].inst2;
2485 }
2486
2487 R300_STATECHANGE(rmesa, fpi[3]);
2488 rmesa->hw.fpi[3].cmd[R300_FPI_CMD_0] = cmdpacket0(R300_US_ALU_ALPHA_ADDR_0, code->alu_end + 1);
2489 for (i = 0; i <= code->alu_end; i++) {
2490 rmesa->hw.fpi[3].cmd[R300_FPI_INSTR_0 + i] = code->alu.inst[i].inst3;
2491 }
2492
2493 R300_STATECHANGE(rmesa, fp);
2494 rmesa->hw.fp.cmd[R300_FP_CNTL0] = code->cur_node | (code->first_node_has_tex << 3);
2495 rmesa->hw.fp.cmd[R300_FP_CNTL1] = code->max_temp_idx;
2496 rmesa->hw.fp.cmd[R300_FP_CNTL2] =
2497 (code->alu_offset << R300_PFS_CNTL_ALU_OFFSET_SHIFT) |
2498 (code->alu_end << R300_PFS_CNTL_ALU_END_SHIFT) |
2499 (code->tex_offset << R300_PFS_CNTL_TEX_OFFSET_SHIFT) |
2500 (code->tex_end << R300_PFS_CNTL_TEX_END_SHIFT);
2501 /* I just want to say, the way these nodes are stored.. weird.. */
2502 for (i = 0, k = (4 - (code->cur_node + 1)); i < 4; i++, k++) {
2503 if (i < (code->cur_node + 1)) {
2504 rmesa->hw.fp.cmd[R300_FP_NODE0 + k] =
2505 (code->node[i].alu_offset << R300_ALU_START_SHIFT) |
2506 (code->node[i].alu_end << R300_ALU_SIZE_SHIFT) |
2507 (code->node[i].tex_offset << R300_TEX_START_SHIFT) |
2508 (code->node[i].tex_end << R300_TEX_SIZE_SHIFT) |
2509 code->node[i].flags;
2510 } else {
2511 rmesa->hw.fp.cmd[R300_FP_NODE0 + (3 - i)] = 0;
2512 }
2513 }
2514
2515 R300_STATECHANGE(rmesa, fpp);
2516 rmesa->hw.fpp.cmd[R300_FPP_CMD_0] = cmdpacket0(R300_PFS_PARAM_0_X, code->const_nr * 4);
2517 for (i = 0; i < code->const_nr; i++) {
2518 rmesa->hw.fpp.cmd[R300_FPP_PARAM_0 + 4 * i + 0] = r300PackFloat24(code->constant[i][0]);
2519 rmesa->hw.fpp.cmd[R300_FPP_PARAM_0 + 4 * i + 1] = r300PackFloat24(code->constant[i][1]);
2520 rmesa->hw.fpp.cmd[R300_FPP_PARAM_0 + 4 * i + 2] = r300PackFloat24(code->constant[i][2]);
2521 rmesa->hw.fpp.cmd[R300_FPP_PARAM_0 + 4 * i + 3] = r300PackFloat24(code->constant[i][3]);
2522 }
2523 }
2524
2525 #define bump_r500fp_count(ptr, new_count) do{\
2526 drm_r300_cmd_header_t* _p=((drm_r300_cmd_header_t*)(ptr));\
2527 int _nc=(new_count)/6; \
2528 assert(_nc < 256); \
2529 if(_nc>_p->r500fp.count)_p->r500fp.count=_nc;\
2530 } while(0)
2531
2532 #define bump_r500fp_const_count(ptr, new_count) do{\
2533 drm_r300_cmd_header_t* _p=((drm_r300_cmd_header_t*)(ptr));\
2534 int _nc=(new_count)/4; \
2535 assert(_nc < 256); \
2536 if(_nc>_p->r500fp.count)_p->r500fp.count=_nc;\
2537 } while(0)
2538
2539 static void r500SetupPixelShader(r300ContextPtr rmesa)
2540 {
2541 GLcontext *ctx = rmesa->radeon.glCtx;
2542 struct r500_fragment_program *fp = (struct r500_fragment_program *)
2543 (char *)ctx->FragmentProgram._Current;
2544 int i;
2545 struct r500_fragment_program_code *code;
2546
2547 if (!fp) /* should only happenen once, just after context is created */
2548 return;
2549
2550 ((drm_r300_cmd_header_t *) rmesa->hw.r500fp.cmd)->r500fp.count = 0;
2551 ((drm_r300_cmd_header_t *) rmesa->hw.r500fp_const.cmd)->r500fp.count = 0;
2552
2553 r500TranslateFragmentShader(rmesa, fp);
2554 if (!fp->translated) {
2555 fprintf(stderr, "%s: No valid fragment shader, exiting\n",
2556 __FUNCTION__);
2557 return;
2558 }
2559 code = &fp->code;
2560
2561 r300SetupTextures(ctx);
2562
2563 R300_STATECHANGE(rmesa, fp);
2564 rmesa->hw.fp.cmd[R500_FP_PIXSIZE] = code->max_temp_idx;
2565
2566 rmesa->hw.fp.cmd[R500_FP_CODE_ADDR] =
2567 R500_US_CODE_START_ADDR(code->inst_offset) |
2568 R500_US_CODE_END_ADDR(code->inst_end);
2569 rmesa->hw.fp.cmd[R500_FP_CODE_RANGE] =
2570 R500_US_CODE_RANGE_ADDR(code->inst_offset) |
2571 R500_US_CODE_RANGE_SIZE(code->inst_end);
2572 rmesa->hw.fp.cmd[R500_FP_CODE_OFFSET] =
2573 R500_US_CODE_OFFSET_ADDR(0); /* FIXME when we add flow control */
2574
2575 R300_STATECHANGE(rmesa, r500fp);
2576 /* Emit our shader... */
2577 for (i = 0; i < code->inst_end+1; i++) {
2578 rmesa->hw.r500fp.cmd[i*6+1] = code->inst[i].inst0;
2579 rmesa->hw.r500fp.cmd[i*6+2] = code->inst[i].inst1;
2580 rmesa->hw.r500fp.cmd[i*6+3] = code->inst[i].inst2;
2581 rmesa->hw.r500fp.cmd[i*6+4] = code->inst[i].inst3;
2582 rmesa->hw.r500fp.cmd[i*6+5] = code->inst[i].inst4;
2583 rmesa->hw.r500fp.cmd[i*6+6] = code->inst[i].inst5;
2584 }
2585
2586 bump_r500fp_count(rmesa->hw.r500fp.cmd, (code->inst_end + 1) * 6);
2587
2588 R300_STATECHANGE(rmesa, r500fp_const);
2589 for (i = 0; i < code->const_nr; i++) {
2590 rmesa->hw.r500fp_const.cmd[R300_FPP_PARAM_0 + 4 * i + 0] = r300PackFloat32(code->constant[i][0]);
2591 rmesa->hw.r500fp_const.cmd[R300_FPP_PARAM_0 + 4 * i + 1] = r300PackFloat32(code->constant[i][1]);
2592 rmesa->hw.r500fp_const.cmd[R300_FPP_PARAM_0 + 4 * i + 2] = r300PackFloat32(code->constant[i][2]);
2593 rmesa->hw.r500fp_const.cmd[R300_FPP_PARAM_0 + 4 * i + 3] = r300PackFloat32(code->constant[i][3]);
2594 }
2595 bump_r500fp_const_count(rmesa->hw.r500fp_const.cmd, code->const_nr * 4);
2596
2597 }
2598
2599 void r300UpdateShaderStates(r300ContextPtr rmesa)
2600 {
2601 GLcontext *ctx;
2602 ctx = rmesa->radeon.glCtx;
2603
2604 r300UpdateTextureState(ctx);
2605 r300SetEarlyZState(ctx);
2606
2607 GLuint fgdepthsrc = R300_FG_DEPTH_SRC_SCAN;
2608 if (current_fragment_program_writes_depth(ctx))
2609 fgdepthsrc = R300_FG_DEPTH_SRC_SHADER;
2610 if (fgdepthsrc != rmesa->hw.fg_depth_src.cmd[1]) {
2611 R300_STATECHANGE(rmesa, fg_depth_src);
2612 rmesa->hw.fg_depth_src.cmd[1] = fgdepthsrc;
2613 }
2614
2615 if (rmesa->radeon.radeonScreen->chip_family >= CHIP_FAMILY_RV515)
2616 r500SetupPixelShader(rmesa);
2617 else
2618 r300SetupPixelShader(rmesa);
2619
2620 if (rmesa->radeon.radeonScreen->chip_family >= CHIP_FAMILY_RV515)
2621 r500SetupRSUnit(ctx);
2622 else
2623 r300SetupRSUnit(ctx);
2624
2625 if ((rmesa->radeon.radeonScreen->chip_flags & RADEON_CHIPSET_TCL))
2626 r300SetupVertexProgram(rmesa);
2627
2628 }
2629
2630 /**
2631 * Called by Mesa after an internal state update.
2632 */
2633 static void r300InvalidateState(GLcontext * ctx, GLuint new_state)
2634 {
2635 r300ContextPtr r300 = R300_CONTEXT(ctx);
2636
2637 _swrast_InvalidateState(ctx, new_state);
2638 _swsetup_InvalidateState(ctx, new_state);
2639 _vbo_InvalidateState(ctx, new_state);
2640 _tnl_InvalidateState(ctx, new_state);
2641 _ae_invalidate_state(ctx, new_state);
2642
2643 if (new_state & (_NEW_BUFFERS | _NEW_COLOR | _NEW_PIXEL)) {
2644 r300UpdateDrawBuffer(ctx);
2645 }
2646
2647 r300UpdateStateParameters(ctx, new_state);
2648
2649 r300->NewGLState |= new_state;
2650 }
2651
2652 /**
2653 * Calculate initial hardware state and register state functions.
2654 * Assumes that the command buffer and state atoms have been
2655 * initialized already.
2656 */
2657 void r300InitState(r300ContextPtr r300)
2658 {
2659 GLcontext *ctx = r300->radeon.glCtx;
2660 GLuint depth_fmt;
2661
2662 radeonInitState(&r300->radeon);
2663
2664 switch (ctx->Visual.depthBits) {
2665 case 16:
2666 r300->state.depth.scale = 1.0 / (GLfloat) 0xffff;
2667 depth_fmt = R300_DEPTHFORMAT_16BIT_INT_Z;
2668 break;
2669 case 24:
2670 r300->state.depth.scale = 1.0 / (GLfloat) 0xffffff;
2671 depth_fmt = R300_DEPTHFORMAT_24BIT_INT_Z_8BIT_STENCIL;
2672 break;
2673 default:
2674 fprintf(stderr, "Error: Unsupported depth %d... exiting\n",
2675 ctx->Visual.depthBits);
2676 _mesa_exit(-1);
2677 }
2678
2679 /* Only have hw stencil when depth buffer is 24 bits deep */
2680 r300->state.stencil.hw_stencil = (ctx->Visual.stencilBits > 0 &&
2681 ctx->Visual.depthBits == 24);
2682
2683 memset(&(r300->state.texture), 0, sizeof(r300->state.texture));
2684
2685 r300ResetHwState(r300);
2686 }
2687
2688 static void r300RenderMode(GLcontext * ctx, GLenum mode)
2689 {
2690 r300ContextPtr rmesa = R300_CONTEXT(ctx);
2691 (void)rmesa;
2692 (void)mode;
2693 }
2694
2695 void r300UpdateClipPlanes( GLcontext *ctx )
2696 {
2697 r300ContextPtr rmesa = R300_CONTEXT(ctx);
2698 GLuint p;
2699
2700 for (p = 0; p < ctx->Const.MaxClipPlanes; p++) {
2701 if (ctx->Transform.ClipPlanesEnabled & (1 << p)) {
2702 GLint *ip = (GLint *)ctx->Transform._ClipUserPlane[p];
2703
2704 R300_STATECHANGE( rmesa, vpucp[p] );
2705 rmesa->hw.vpucp[p].cmd[R300_VPUCP_X] = ip[0];
2706 rmesa->hw.vpucp[p].cmd[R300_VPUCP_Y] = ip[1];
2707 rmesa->hw.vpucp[p].cmd[R300_VPUCP_Z] = ip[2];
2708 rmesa->hw.vpucp[p].cmd[R300_VPUCP_W] = ip[3];
2709 }
2710 }
2711 }
2712
2713 /**
2714 * Initialize driver's state callback functions
2715 */
2716 void r300InitStateFuncs(struct dd_function_table *functions)
2717 {
2718 radeonInitStateFuncs(functions);
2719
2720 functions->UpdateState = r300InvalidateState;
2721 functions->AlphaFunc = r300AlphaFunc;
2722 functions->BlendColor = r300BlendColor;
2723 functions->BlendEquationSeparate = r300BlendEquationSeparate;
2724 functions->BlendFuncSeparate = r300BlendFuncSeparate;
2725 functions->Enable = r300Enable;
2726 functions->ColorMask = r300ColorMask;
2727 functions->DepthFunc = r300DepthFunc;
2728 functions->DepthMask = r300DepthMask;
2729 functions->CullFace = r300CullFace;
2730 functions->Fogfv = r300Fogfv;
2731 functions->FrontFace = r300FrontFace;
2732 functions->ShadeModel = r300ShadeModel;
2733
2734 /* ARB_point_parameters */
2735 functions->PointParameterfv = r300PointParameter;
2736
2737 /* Stencil related */
2738 functions->StencilFuncSeparate = r300StencilFuncSeparate;
2739 functions->StencilMaskSeparate = r300StencilMaskSeparate;
2740 functions->StencilOpSeparate = r300StencilOpSeparate;
2741
2742 /* Viewport related */
2743 functions->Viewport = r300Viewport;
2744 functions->DepthRange = r300DepthRange;
2745 functions->PointSize = r300PointSize;
2746 functions->LineWidth = r300LineWidth;
2747
2748 functions->PolygonOffset = r300PolygonOffset;
2749 functions->PolygonMode = r300PolygonMode;
2750
2751 functions->RenderMode = r300RenderMode;
2752
2753 functions->ClipPlane = r300ClipPlane;
2754 }