c75f2154e1a92b93767f271bde406d26c4a11c66
[profile/ivi/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  * Authors:
34  *   Nicolai Haehnle <prefect_@gmx.net>
35  */
36
37 #include "glheader.h"
38 #include "state.h"
39 #include "imports.h"
40 #include "enums.h"
41 #include "macros.h"
42 #include "context.h"
43 #include "dd.h"
44 #include "simple_list.h"
45
46 #include "api_arrayelt.h"
47 #include "swrast/swrast.h"
48 #include "swrast_setup/swrast_setup.h"
49 #include "array_cache/acache.h"
50 #include "tnl/tnl.h"
51 #include "texformat.h"
52
53 #include "radeon_ioctl.h"
54 #include "radeon_state.h"
55 #include "r300_context.h"
56 #include "r300_ioctl.h"
57 #include "r300_state.h"
58 #include "r300_reg.h"
59 #include "r300_program.h"
60 #include "r300_emit.h"
61 #include "r300_fixed_pipelines.h"
62
63
64 static void r300AlphaFunc(GLcontext * ctx, GLenum func, GLfloat ref)
65 {
66         r300ContextPtr rmesa = R300_CONTEXT(ctx);
67         int pp_misc = rmesa->hw.at.cmd[R300_AT_ALPHA_TEST];
68         GLubyte refByte;
69
70         CLAMPED_FLOAT_TO_UBYTE(refByte, ref);
71
72         R300_STATECHANGE(rmesa, at);
73
74         pp_misc &= ~(R300_ALPHA_TEST_OP_MASK | R300_REF_ALPHA_MASK);
75         pp_misc |= (refByte & R300_REF_ALPHA_MASK);
76
77         switch (func) {
78         case GL_NEVER:
79                 pp_misc |= R300_ALPHA_TEST_FAIL;
80                 break;
81         case GL_LESS:
82                 pp_misc |= R300_ALPHA_TEST_LESS;
83                 break;
84         case GL_EQUAL:
85                 pp_misc |= R300_ALPHA_TEST_EQUAL;
86                 break;
87         case GL_LEQUAL:
88                 pp_misc |= R300_ALPHA_TEST_LEQUAL;
89                 break;
90         case GL_GREATER:
91                 pp_misc |= R300_ALPHA_TEST_GREATER;
92                 break;
93         case GL_NOTEQUAL:
94                 pp_misc |= R300_ALPHA_TEST_NEQUAL;
95                 break;
96         case GL_GEQUAL:
97                 pp_misc |= R300_ALPHA_TEST_GEQUAL;
98                 break;
99         case GL_ALWAYS:
100                 pp_misc |= R300_ALPHA_TEST_PASS;
101                 break;
102         }
103
104         rmesa->hw.at.cmd[R300_AT_ALPHA_TEST] = pp_misc;
105 }
106
107 static void r300BlendColor(GLcontext * ctx, const GLfloat cf[4])
108 {
109         GLubyte color[4];
110         r300ContextPtr rmesa = R300_CONTEXT(ctx);
111         fprintf(stderr, "%s:%s is not implemented yet. Fixme !\n", __FILE__, __FUNCTION__);
112         #if 0
113         R200_STATECHANGE(rmesa, ctx);
114         CLAMPED_FLOAT_TO_UBYTE(color[0], cf[0]);
115         CLAMPED_FLOAT_TO_UBYTE(color[1], cf[1]);
116         CLAMPED_FLOAT_TO_UBYTE(color[2], cf[2]);
117         CLAMPED_FLOAT_TO_UBYTE(color[3], cf[3]);
118         if (rmesa->radeon.radeonScreen->drmSupportsBlendColor)
119                 rmesa->hw.ctx.cmd[CTX_RB3D_BLENDCOLOR] =
120                     radeonPackColor(4, color[0], color[1], color[2], color[3]);
121         #endif
122 }
123
124 /**
125  * Calculate the hardware blend factor setting.  This same function is used
126  * for source and destination of both alpha and RGB.
127  *
128  * \returns
129  * The hardware register value for the specified blend factor.  This value
130  * will need to be shifted into the correct position for either source or
131  * destination factor.
132  *
133  * \todo
134  * Since the two cases where source and destination are handled differently
135  * are essentially error cases, they should never happen.  Determine if these
136  * cases can be removed.
137  */
138 static int blend_factor(GLenum factor, GLboolean is_src)
139 {
140         int func;
141
142         switch (factor) {
143         case GL_ZERO:
144                 func = R200_BLEND_GL_ZERO;
145                 break;
146         case GL_ONE:
147                 func = R200_BLEND_GL_ONE;
148                 break;
149         case GL_DST_COLOR:
150                 func = R200_BLEND_GL_DST_COLOR;
151                 break;
152         case GL_ONE_MINUS_DST_COLOR:
153                 func = R200_BLEND_GL_ONE_MINUS_DST_COLOR;
154                 break;
155         case GL_SRC_COLOR:
156                 func = R200_BLEND_GL_SRC_COLOR;
157                 break;
158         case GL_ONE_MINUS_SRC_COLOR:
159                 func = R200_BLEND_GL_ONE_MINUS_SRC_COLOR;
160                 break;
161         case GL_SRC_ALPHA:
162                 func = R200_BLEND_GL_SRC_ALPHA;
163                 break;
164         case GL_ONE_MINUS_SRC_ALPHA:
165                 func = R200_BLEND_GL_ONE_MINUS_SRC_ALPHA;
166                 break;
167         case GL_DST_ALPHA:
168                 func = R200_BLEND_GL_DST_ALPHA;
169                 break;
170         case GL_ONE_MINUS_DST_ALPHA:
171                 func = R200_BLEND_GL_ONE_MINUS_DST_ALPHA;
172                 break;
173         case GL_SRC_ALPHA_SATURATE:
174                 func =
175                     (is_src) ? R200_BLEND_GL_SRC_ALPHA_SATURATE :
176                     R200_BLEND_GL_ZERO;
177                 break;
178         case GL_CONSTANT_COLOR:
179                 func = R200_BLEND_GL_CONST_COLOR;
180                 break;
181         case GL_ONE_MINUS_CONSTANT_COLOR:
182                 func = R200_BLEND_GL_ONE_MINUS_CONST_COLOR;
183                 break;
184         case GL_CONSTANT_ALPHA:
185                 func = R200_BLEND_GL_CONST_ALPHA;
186                 break;
187         case GL_ONE_MINUS_CONSTANT_ALPHA:
188                 func = R200_BLEND_GL_ONE_MINUS_CONST_ALPHA;
189                 break;
190         default:
191                 func = (is_src) ? R200_BLEND_GL_ONE : R200_BLEND_GL_ZERO;
192         }
193         return func;
194 }
195
196 /**
197  * Sets both the blend equation and the blend function.
198  * This is done in a single
199  * function because some blend equations (i.e., \c GL_MIN and \c GL_MAX)
200  * change the interpretation of the blend function.
201  * Also, make sure that blend function and blend equation are set to their default
202  * value if color blending is not enabled, since at least blend equations GL_MIN
203  * and GL_FUNC_REVERSE_SUBTRACT will cause wrong results otherwise for
204  * unknown reasons.
205  */
206
207 /* helper function */
208 static void r300_set_blend_cntl(r300ContextPtr rmesa, int func, int eqn, int cbits, int funcA, int eqnA)
209 {
210         GLuint new_ablend, new_cblend;
211
212         #if 0
213         fprintf(stderr, "eqnA=%08x funcA=%08x eqn=%08x func=%08x cbits=%08x\n", eqnA, funcA, eqn, func, cbits);
214         #endif
215         new_ablend = eqnA | funcA;
216         new_cblend = eqn | func;
217         if(funcA == func){
218                 new_cblend |=  R300_BLEND_NO_SEPARATE;
219                 }
220         new_cblend |= cbits;
221         
222         if((new_ablend != rmesa->hw.bld.cmd[R300_BLD_ABLEND])
223                 || (new_cblend != rmesa->hw.bld.cmd[R300_BLD_CBLEND])){
224                 R300_STATECHANGE(rmesa, bld);
225                 rmesa->hw.bld.cmd[R300_BLD_ABLEND]=new_ablend;
226                 rmesa->hw.bld.cmd[R300_BLD_CBLEND]=new_cblend;
227                 }
228 }
229
230 static void r300_set_blend_state(GLcontext * ctx)
231 {
232         r300ContextPtr rmesa = R300_CONTEXT(ctx);
233         #if 0
234         GLuint cntl = rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] &
235             ~(R300_ROP_ENABLE | R300_ALPHA_BLEND_ENABLE |
236               R300_SEPARATE_ALPHA_ENABLE);
237         #endif
238
239         int func = (R200_BLEND_GL_ONE << R200_SRC_BLEND_SHIFT) |
240             (R200_BLEND_GL_ZERO << R200_DST_BLEND_SHIFT);
241         int eqn = R200_COMB_FCN_ADD_CLAMP;
242         int funcA = (R200_BLEND_GL_ONE << R200_SRC_BLEND_SHIFT) |
243             (R200_BLEND_GL_ZERO << R200_DST_BLEND_SHIFT);
244         int eqnA = R200_COMB_FCN_ADD_CLAMP;
245
246
247         if (rmesa->radeon.radeonScreen->drmSupportsBlendColor) {
248                 if (ctx->Color._LogicOpEnabled) {
249                         #if 0
250                         rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] =
251                             cntl | R300_ROP_ENABLE;
252                         #endif
253                         r300_set_blend_cntl(rmesa,
254                                 func, eqn, 0,
255                                 func, eqn);
256                         return;
257                 } else if (ctx->Color.BlendEnabled) {
258                         #if 0
259                         rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] =
260                             cntl | R300_ALPHA_BLEND_ENABLE |
261                             R300_SEPARATE_ALPHA_ENABLE;
262                         #endif
263                 } else {
264                         #if 0
265                         rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] = cntl;
266                         #endif
267                         r300_set_blend_cntl(rmesa,
268                                 func, eqn, 0,
269                                 func, eqn);
270                         return;
271                 }
272         } else {
273                 if (ctx->Color._LogicOpEnabled) {
274                         #if 0
275                         rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] =
276                             cntl | R300_ROP_ENABLE;
277                         rmesa->hw.ctx.cmd[CTX_RB3D_BLENDCNTL] = eqn | func;
278                         #endif
279                         return;
280                 } else if (ctx->Color.BlendEnabled) {
281                         #if 0
282                         rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] =
283                             cntl | R300_ALPHA_BLEND_ENABLE;
284                         #endif
285                 } else {
286                         #if 0
287                         rmesa->hw.ctx.cmd[CTX_RB3D_CNTL] = cntl;
288                         rmesa->hw.ctx.cmd[CTX_RB3D_BLENDCNTL] = eqn | func;
289                         #endif
290                         r300_set_blend_cntl(rmesa,
291                                 func, eqn, 0,
292                                 func, eqn);
293                         return;
294                 }
295         }
296
297         func =
298             (blend_factor(ctx->Color.BlendSrcRGB, GL_TRUE) <<
299              R200_SRC_BLEND_SHIFT) | (blend_factor(ctx->Color.BlendDstRGB,
300                                                    GL_FALSE) <<
301                                       R200_DST_BLEND_SHIFT);
302
303         switch (ctx->Color.BlendEquationRGB) {
304         case GL_FUNC_ADD:
305                 eqn = R300_COMB_FCN_ADD_CLAMP;
306                 break;
307
308         case GL_FUNC_SUBTRACT:
309                 eqn = R300_COMB_FCN_SUB_CLAMP;
310                 break;
311
312         case GL_FUNC_REVERSE_SUBTRACT:
313                 eqn = R200_COMB_FCN_RSUB_CLAMP;
314                 break;
315
316         case GL_MIN:
317                 eqn = R200_COMB_FCN_MIN;
318                 func = (R200_BLEND_GL_ONE << R200_SRC_BLEND_SHIFT) |
319                     (R200_BLEND_GL_ONE << R200_DST_BLEND_SHIFT);
320                 break;
321
322         case GL_MAX:
323                 eqn = R200_COMB_FCN_MAX;
324                 func = (R200_BLEND_GL_ONE << R200_SRC_BLEND_SHIFT) |
325                     (R200_BLEND_GL_ONE << R200_DST_BLEND_SHIFT);
326                 break;
327
328         default:
329                 fprintf(stderr,
330                         "[%s:%u] Invalid RGB blend equation (0x%04x).\n",
331                         __func__, __LINE__, ctx->Color.BlendEquationRGB);
332                 return;
333         }
334
335         if (!rmesa->radeon.radeonScreen->drmSupportsBlendColor) {
336                 #if 0
337                 rmesa->hw.ctx.cmd[CTX_RB3D_BLENDCNTL] = eqn | func;
338                 #endif
339                 return;
340         }
341
342         funcA =
343             (blend_factor(ctx->Color.BlendSrcA, GL_TRUE) <<
344              R200_SRC_BLEND_SHIFT) | (blend_factor(ctx->Color.BlendDstA,
345                                                    GL_FALSE) <<
346                                       R200_DST_BLEND_SHIFT);
347
348         switch (ctx->Color.BlendEquationA) {
349         case GL_FUNC_ADD:
350                 eqnA = R300_COMB_FCN_ADD_CLAMP;
351                 break;
352
353         case GL_FUNC_SUBTRACT:
354                 eqnA = R300_COMB_FCN_SUB_CLAMP;
355                 break;
356
357         case GL_FUNC_REVERSE_SUBTRACT:
358                 eqnA = R200_COMB_FCN_RSUB_CLAMP;
359                 break;
360
361         case GL_MIN:
362                 eqnA = R200_COMB_FCN_MIN;
363                 funcA = (R200_BLEND_GL_ONE << R200_SRC_BLEND_SHIFT) |
364                     (R200_BLEND_GL_ONE << R200_DST_BLEND_SHIFT);
365                 break;
366
367         case GL_MAX:
368                 eqnA = R200_COMB_FCN_MAX;
369                 funcA = (R200_BLEND_GL_ONE << R200_SRC_BLEND_SHIFT) |
370                     (R200_BLEND_GL_ONE << R200_DST_BLEND_SHIFT);
371                 break;
372
373         default:
374                 fprintf(stderr, "[%s:%u] Invalid A blend equation (0x%04x).\n",
375                         __func__, __LINE__, ctx->Color.BlendEquationA);
376                 return;
377         }
378
379         r300_set_blend_cntl(rmesa,
380                 func, eqn, R300_BLEND_UNKNOWN | R300_BLEND_ENABLE,
381                 funcA, eqnA);
382         r300_set_blend_cntl(rmesa,
383                 func, eqn, R300_BLEND_UNKNOWN | R300_BLEND_ENABLE,
384                 funcA, eqnA);
385 }
386
387 static void r300BlendEquationSeparate(GLcontext * ctx,
388                                       GLenum modeRGB, GLenum modeA)
389 {
390         r300_set_blend_state(ctx);
391 }
392
393 static void r300BlendFuncSeparate(GLcontext * ctx,
394                                   GLenum sfactorRGB, GLenum dfactorRGB,
395                                   GLenum sfactorA, GLenum dfactorA)
396 {
397         r300_set_blend_state(ctx);
398 }
399
400 /**
401  * Update our tracked culling state based on Mesa's state.
402  */
403 static void r300UpdateCulling(GLcontext* ctx)
404 {
405         r300ContextPtr r300 = R300_CONTEXT(ctx);
406         uint32_t val = 0;
407
408         R300_STATECHANGE(r300, cul);
409         if (ctx->Polygon.CullFlag) {
410                 if (ctx->Polygon.CullFaceMode == GL_FRONT_AND_BACK)
411                         val = R300_CULL_FRONT|R300_CULL_BACK;
412                 else if (ctx->Polygon.CullFaceMode == GL_FRONT)
413                         val = R300_CULL_FRONT;
414                 else
415                         val = R300_CULL_BACK;
416
417                 if (ctx->Polygon.FrontFace == GL_CW)
418                         val |= R300_FRONT_FACE_CW;
419                 else
420                         val |= R300_FRONT_FACE_CCW;
421         }
422
423         r300->hw.cul.cmd[R300_CUL_CULL] = val;
424 }
425
426
427 /**
428  * Handle glEnable()/glDisable().
429  *
430  * \note Mesa already filters redundant calls to glEnable/glDisable.
431  */
432 static void r300Enable(GLcontext* ctx, GLenum cap, GLboolean state)
433 {
434         r300ContextPtr r300 = R300_CONTEXT(ctx);
435         uint32_t newval;
436
437         if (RADEON_DEBUG & DEBUG_STATE)
438                 fprintf(stderr, "%s( %s = %s )\n", __FUNCTION__,
439                         _mesa_lookup_enum_by_nr(cap),
440                         state ? "GL_TRUE" : "GL_FALSE");
441
442         switch (cap) {
443                 /* Fast track this one...
444                  */
445         case GL_TEXTURE_1D:
446         case GL_TEXTURE_2D:
447         case GL_TEXTURE_3D:
448                 break;
449
450         case GL_ALPHA_TEST:
451                 R200_STATECHANGE(r300, at);
452                 if (state) {
453                         r300->hw.at.cmd[R300_AT_ALPHA_TEST] |=
454                             R300_ALPHA_TEST_ENABLE;
455                 } else {
456                         r300->hw.at.cmd[R300_AT_ALPHA_TEST] |=
457                             ~R300_ALPHA_TEST_ENABLE;
458                 }
459                 break;
460
461         case GL_BLEND:
462         case GL_COLOR_LOGIC_OP:
463                 r300_set_blend_state(ctx);
464                 break;
465
466         case GL_DEPTH_TEST:
467                 R300_STATECHANGE(r300, zs);
468
469                 if (state) {
470                         if (ctx->Depth.Mask)
471                                 newval = R300_RB3D_Z_TEST_AND_WRITE;
472                         else
473                                 newval = R300_RB3D_Z_TEST;
474                 } else
475                         newval = 0;
476
477                 r300->hw.zs.cmd[R300_ZS_CNTL_0] = newval;
478                 break;
479
480         case GL_STENCIL_TEST:
481
482                 {
483                 static int stencil=1;
484                 if(stencil){
485                         fprintf(stderr, "%s:%s - do not know how to enable stencil. Help me !\n",
486                                 __FILE__, __FUNCTION__);
487                         stencil=0;
488                         }
489                 }
490
491                 if (r300->state.hw_stencil) {
492                         //fprintf(stderr, "Stencil %s\n", state ? "enabled" : "disabled");
493                         R300_STATECHANGE(r300, zs);
494                         if (state) {
495                                 r300->hw.zs.cmd[R300_ZS_CNTL_0] |=
496                                     R300_RB3D_STENCIL_ENABLE;
497                         } else {
498                                 r300->hw.zs.cmd[R300_ZS_CNTL_0] &=
499                                     ~R300_RB3D_STENCIL_ENABLE;
500                         }
501                 } else {
502                         FALLBACK(&r300->radeon, RADEON_FALLBACK_STENCIL, state);
503                 }
504                 break;
505
506         case GL_CULL_FACE:
507                 r300UpdateCulling(ctx);
508                 break;
509         case GL_VERTEX_PROGRAM_ARB:
510                 //TCL_FALLBACK(rmesa->glCtx, R200_TCL_FALLBACK_TCL_DISABLE, state);
511         break;
512
513         default:
514                 radeonEnable(ctx, cap, state);
515                 return;
516         }
517 }
518
519
520 /**
521  * Change the culling mode.
522  *
523  * \note Mesa already filters redundant calls to this function.
524  */
525 static void r300CullFace(GLcontext* ctx, GLenum mode)
526 {
527         (void)mode;
528
529         r300UpdateCulling(ctx);
530 }
531
532
533 /**
534  * Change the polygon orientation.
535  *
536  * \note Mesa already filters redundant calls to this function.
537  */
538 static void r300FrontFace(GLcontext* ctx, GLenum mode)
539 {
540         (void)mode;
541
542         r300UpdateCulling(ctx);
543 }
544
545
546 /**
547  * Change the depth testing function.
548  *
549  * \note Mesa already filters redundant calls to this function.
550  */
551 static void r300DepthFunc(GLcontext* ctx, GLenum func)
552 {
553         r300ContextPtr r300 = R300_CONTEXT(ctx);
554
555         R300_STATECHANGE(r300, zs);
556
557         r300->hw.zs.cmd[R300_ZS_CNTL_1] &= ~(R300_ZS_MASK << R300_RB3D_ZS1_DEPTH_FUNC_SHIFT);
558
559         switch(func) {
560         case GL_NEVER:
561                 r300->hw.zs.cmd[R300_ZS_CNTL_1] |= R300_ZS_NEVER << R300_RB3D_ZS1_DEPTH_FUNC_SHIFT;
562                 break;
563         case GL_LESS:
564                 r300->hw.zs.cmd[R300_ZS_CNTL_1] |= R300_ZS_LESS << R300_RB3D_ZS1_DEPTH_FUNC_SHIFT;
565                 break;
566         case GL_EQUAL:
567                 r300->hw.zs.cmd[R300_ZS_CNTL_1] |= R300_ZS_EQUAL << R300_RB3D_ZS1_DEPTH_FUNC_SHIFT;
568                 break;
569         case GL_LEQUAL:
570                 r300->hw.zs.cmd[R300_ZS_CNTL_1] |= R300_ZS_LEQUAL << R300_RB3D_ZS1_DEPTH_FUNC_SHIFT;
571                 break;
572         case GL_GREATER:
573                 r300->hw.zs.cmd[R300_ZS_CNTL_1] |= R300_ZS_GREATER << R300_RB3D_ZS1_DEPTH_FUNC_SHIFT;
574                 break;
575         case GL_NOTEQUAL:
576                 r300->hw.zs.cmd[R300_ZS_CNTL_1] |= R300_ZS_NOTEQUAL << R300_RB3D_ZS1_DEPTH_FUNC_SHIFT;
577                 break;
578         case GL_GEQUAL:
579                 r300->hw.zs.cmd[R300_ZS_CNTL_1] |= R300_ZS_GEQUAL << R300_RB3D_ZS1_DEPTH_FUNC_SHIFT;
580                 break;
581         case GL_ALWAYS:
582                 r300->hw.zs.cmd[R300_ZS_CNTL_1] |= R300_ZS_ALWAYS << R300_RB3D_ZS1_DEPTH_FUNC_SHIFT;
583                 break;
584         }
585
586 }
587
588
589 /**
590  * Enable/Disable depth writing.
591  *
592  * \note Mesa already filters redundant calls to this function.
593  */
594 static void r300DepthMask(GLcontext* ctx, GLboolean mask)
595 {
596         r300ContextPtr r300 = R300_CONTEXT(ctx);
597
598         if (!ctx->Depth.Test)
599                 return;
600
601         R300_STATECHANGE(r300, zs);
602         r300->hw.zs.cmd[R300_ZS_CNTL_0] = mask
603                 ? R300_RB3D_Z_TEST_AND_WRITE : R300_RB3D_Z_TEST;
604 }
605
606
607 /**
608  * Handle glColorMask()
609  */
610 static void r300ColorMask(GLcontext* ctx,
611                           GLboolean r, GLboolean g, GLboolean b, GLboolean a)
612 {
613         r300ContextPtr r300 = R300_CONTEXT(ctx);
614         int mask = (b << 0) | (g << 1) | (r << 2) | (a << 3);
615
616         if (mask != r300->hw.cmk.cmd[R300_CMK_COLORMASK]) {
617                 R300_STATECHANGE(r300, cmk);
618                 r300->hw.cmk.cmd[R300_CMK_COLORMASK] = mask;
619         }
620 }
621
622 /* =============================================================
623  * Point state
624  */
625 static void r300PointSize(GLcontext * ctx, GLfloat size)
626 {
627         r300ContextPtr r300 = R300_CONTEXT(ctx);
628
629         /* This might need fixing later */
630         R300_STATECHANGE(r300, vps);
631         r300->hw.vps.cmd[R300_VPS_POINTSIZE] = r300PackFloat32(1.0);
632 }
633 /* =============================================================
634  * Stencil
635  */
636
637  static int translate_stencil_func(int func)
638  {
639         switch (func) {
640         case GL_NEVER:
641                     return R300_ZS_NEVER;
642                 break;
643         case GL_LESS:
644                     return R300_ZS_LESS;
645                 break;
646         case GL_EQUAL:
647                     return R300_ZS_EQUAL;
648                 break;
649         case GL_LEQUAL:
650                     return R300_ZS_LEQUAL;
651                 break;
652         case GL_GREATER:
653                     return R300_ZS_GREATER;
654                 break;
655         case GL_NOTEQUAL:
656                     return R300_ZS_NOTEQUAL;
657                 break;
658         case GL_GEQUAL:
659                     return R300_ZS_GEQUAL;
660                 break;
661         case GL_ALWAYS:
662                     return R300_ZS_ALWAYS;
663                 break;
664         }
665  return 0;
666  }
667
668  static int translate_stencil_op(int op)
669 {
670         switch (op) {
671         case GL_KEEP:
672                     return R300_ZS_KEEP;
673         case GL_ZERO:
674                     return R300_ZS_ZERO;
675         case GL_REPLACE:
676                     return R300_ZS_REPLACE;
677         case GL_INCR:
678                     return R300_ZS_INCR;
679         case GL_DECR:
680                     return R300_ZS_DECR;
681         case GL_INCR_WRAP_EXT:
682                     return R300_ZS_INCR_WRAP;
683         case GL_DECR_WRAP_EXT:
684                     return R300_ZS_DECR_WRAP;
685         case GL_INVERT:
686                     return R300_ZS_INVERT;
687         }
688 }
689
690 static void r300StencilFunc(GLcontext * ctx, GLenum func,
691                             GLint ref, GLuint mask)
692 {
693         r300ContextPtr rmesa = R300_CONTEXT(ctx);
694         GLuint refmask = ((ctx->Stencil.Ref[0] << R300_RB3D_ZS2_STENCIL_REF_SHIFT) |
695                           (ctx->Stencil.
696                            ValueMask[0] << R300_RB3D_ZS2_STENCIL_MASK_SHIFT));
697         GLuint flag;
698
699         R200_STATECHANGE(rmesa, zs);
700
701         rmesa->hw.zs.cmd[R300_ZS_CNTL_1] &= ~(
702                 (R300_ZS_MASK << R300_RB3D_ZS1_FRONT_FUNC_SHIFT)
703                 | (R300_ZS_MASK << R300_RB3D_ZS1_BACK_FUNC_SHIFT));
704         rmesa->hw.zs.cmd[R300_ZS_CNTL_2] &=  ~((R300_ZS_MASK << R300_RB3D_ZS2_STENCIL_REF_SHIFT) |
705                                                 (R300_ZS_MASK << R300_RB3D_ZS2_STENCIL_MASK_SHIFT));
706
707         flag = translate_stencil_func(ctx->Stencil.Function[0]);
708
709         rmesa->hw.zs.cmd[R300_ZS_CNTL_1] |= (flag << R300_RB3D_ZS1_FRONT_FUNC_SHIFT)
710                                           | (flag << R300_RB3D_ZS1_BACK_FUNC_SHIFT);
711         rmesa->hw.zs.cmd[R300_ZS_CNTL_2] |= refmask;
712 }
713
714 static void r300StencilMask(GLcontext * ctx, GLuint mask)
715 {
716         r300ContextPtr rmesa = R300_CONTEXT(ctx);
717
718         R200_STATECHANGE(rmesa, zs);
719         rmesa->hw.zs.cmd[R300_ZS_CNTL_2]  &= ~(R300_ZS_MASK << R300_RB3D_ZS2_STENCIL_WRITE_MASK_SHIFT);
720         rmesa->hw.zs.cmd[R300_ZS_CNTL_2] |= ctx->Stencil.WriteMask[0] << R300_RB3D_ZS2_STENCIL_WRITE_MASK_SHIFT;
721 }
722
723
724 static void r300StencilOp(GLcontext * ctx, GLenum fail,
725                           GLenum zfail, GLenum zpass)
726 {
727         r300ContextPtr rmesa = R300_CONTEXT(ctx);
728
729         R200_STATECHANGE(rmesa, zs);
730                 /* It is easier to mask what's left.. */
731         rmesa->hw.zs.cmd[R300_ZS_CNTL_1] &= (R300_ZS_MASK << R300_RB3D_ZS1_DEPTH_FUNC_SHIFT);
732
733         rmesa->hw.zs.cmd[R300_ZS_CNTL_1] |=
734                  (translate_stencil_op(ctx->Stencil.FailFunc[0]) << R300_RB3D_ZS1_FRONT_FAIL_OP_SHIFT)
735                 |(translate_stencil_op(ctx->Stencil.ZFailFunc[0]) << R300_RB3D_ZS1_FRONT_ZFAIL_OP_SHIFT)
736                 |(translate_stencil_op(ctx->Stencil.ZPassFunc[0]) << R300_RB3D_ZS1_FRONT_ZPASS_OP_SHIFT)
737                 |(translate_stencil_op(ctx->Stencil.FailFunc[0]) << R300_RB3D_ZS1_BACK_FAIL_OP_SHIFT)
738                 |(translate_stencil_op(ctx->Stencil.ZFailFunc[0]) << R300_RB3D_ZS1_BACK_ZFAIL_OP_SHIFT)
739                 |(translate_stencil_op(ctx->Stencil.ZPassFunc[0]) << R300_RB3D_ZS1_BACK_ZPASS_OP_SHIFT);
740
741 }
742
743 static void r300ClearStencil(GLcontext * ctx, GLint s)
744 {
745         r300ContextPtr rmesa = R300_CONTEXT(ctx);
746
747         /* Not sure whether this is correct.. */
748         R200_STATECHANGE(rmesa, zs);
749         rmesa->hw.zs.cmd[R300_ZS_CNTL_2] =
750             ((GLuint) ctx->Stencil.Clear |
751              (0xff << R200_STENCIL_MASK_SHIFT) |
752              (ctx->Stencil.WriteMask[0] << R200_STENCIL_WRITEMASK_SHIFT));
753 }
754
755 /* =============================================================
756  * Window position and viewport transformation
757  */
758
759 /*
760  * To correctly position primitives:
761  */
762 #define SUBPIXEL_X 0.125
763 #define SUBPIXEL_Y 0.125
764
765 void r300UpdateWindow(GLcontext * ctx)
766 {
767         r300ContextPtr rmesa = R300_CONTEXT(ctx);
768         __DRIdrawablePrivate *dPriv = rmesa->radeon.dri.drawable;
769         GLfloat xoffset = dPriv ? (GLfloat) dPriv->x : 0;
770         GLfloat yoffset = dPriv ? (GLfloat) dPriv->y + dPriv->h : 0;
771         const GLfloat *v = ctx->Viewport._WindowMap.m;
772
773         GLfloat sx = v[MAT_SX];
774         GLfloat tx = v[MAT_TX] + xoffset + SUBPIXEL_X;
775         GLfloat sy = -v[MAT_SY];
776         GLfloat ty = (-v[MAT_TY]) + yoffset + SUBPIXEL_Y;
777         GLfloat sz = v[MAT_SZ] * rmesa->state.depth.scale;
778         GLfloat tz = v[MAT_TZ] * rmesa->state.depth.scale;
779
780         R300_FIREVERTICES(rmesa);
781         R300_STATECHANGE(rmesa, vpt);
782
783         rmesa->hw.vpt.cmd[R300_VPT_XSCALE]  = r300PackFloat32(sx);
784         rmesa->hw.vpt.cmd[R300_VPT_XOFFSET] = r300PackFloat32(tx);
785         rmesa->hw.vpt.cmd[R300_VPT_YSCALE]  = r300PackFloat32(sy);
786         rmesa->hw.vpt.cmd[R300_VPT_YOFFSET] = r300PackFloat32(ty);
787         rmesa->hw.vpt.cmd[R300_VPT_ZSCALE]  = r300PackFloat32(sz);
788         rmesa->hw.vpt.cmd[R300_VPT_ZOFFSET] = r300PackFloat32(tz);
789 }
790
791 static void r300Viewport(GLcontext * ctx, GLint x, GLint y,
792                          GLsizei width, GLsizei height)
793 {
794         /* Don't pipeline viewport changes, conflict with window offset
795          * setting below.  Could apply deltas to rescue pipelined viewport
796          * values, or keep the originals hanging around.
797          */
798         R200_FIREVERTICES(R200_CONTEXT(ctx));
799         r300UpdateWindow(ctx);
800 }
801
802 static void r300DepthRange(GLcontext * ctx, GLclampd nearval, GLclampd farval)
803 {
804         r300UpdateWindow(ctx);
805 }
806
807 /* Routing and texture-related */
808
809 void r300_setup_routing(GLcontext *ctx, GLboolean immediate)
810 {
811         int i, count=0,reg=0;
812         GLuint dw, mask;
813         TNLcontext *tnl = TNL_CONTEXT(ctx);
814         struct vertex_buffer *VB = &tnl->vb;
815         r300ContextPtr r300 = R300_CONTEXT(ctx);
816
817
818         /* Stage 1 - input to VAP */
819
820         /* Assign register number automatically, retaining it in rmesa->state.reg */
821
822         /* Note: immediate vertex data includes all coordinates.
823         To save bandwidth use either VBUF or state-based vertex generation */
824
825         #define CONFIGURE_AOS(v, o, r, f) \
826                 {\
827                 if (RADEON_DEBUG & DEBUG_STATE)fprintf(stderr, "Enabling "#r "\n"); \
828                 if(immediate){ \
829                         r300->state.aos[count].element_size=4; \
830                         r300->state.aos[count].stride=4; \
831                         r300->state.aos[count].ncomponents=4; \
832                         } else { \
833                         r300->state.aos[count].element_size=v->size; \
834                         r300->state.aos[count].stride=v->size; \
835                         r300->state.aos[count].ncomponents=v->size; \
836                         } \
837                 r300->state.aos[count].offset=o; \
838                 r300->state.aos[count].reg=reg; \
839                 r300->state.aos[count].format=(f); \
840                 r300->state.vap_reg.r=reg; \
841                 count++; \
842                 reg++; \
843                 }
844
845                 /* All offsets are 0 - for use by immediate mode.
846                 Should change later to handle vertex buffers */
847         if(tnl->render_inputs & _TNL_BIT_POS)
848                 CONFIGURE_AOS(VB->ObjPtr, 0, i_coords, AOS_FORMAT_FLOAT);
849         if(tnl->render_inputs & _TNL_BIT_NORMAL)
850                 CONFIGURE_AOS(VB->NormalPtr, 0, i_normal, AOS_FORMAT_FLOAT);
851
852         if(tnl->render_inputs & _TNL_BIT_COLOR0)
853                 CONFIGURE_AOS(VB->ColorPtr[0], 0, i_color[0], AOS_FORMAT_FLOAT_COLOR);
854         if(tnl->render_inputs & _TNL_BIT_COLOR1)
855                 CONFIGURE_AOS(VB->SecondaryColorPtr[0], 0, i_color[1], AOS_FORMAT_FLOAT_COLOR);
856
857         if(tnl->render_inputs & _TNL_BIT_FOG)
858                 CONFIGURE_AOS(VB->FogCoordPtr, 0, i_fog, AOS_FORMAT_FLOAT);
859
860         for(i=0;i < ctx->Const.MaxTextureUnits;i++)
861                 if(tnl->render_inputs & (_TNL_BIT_TEX0<<i))
862                         CONFIGURE_AOS(VB->TexCoordPtr[i], 0, i_tex[i], AOS_FORMAT_FLOAT);
863
864         if(tnl->render_inputs & _TNL_BIT_INDEX)
865                 CONFIGURE_AOS(VB->IndexPtr[0], 0, i_index, AOS_FORMAT_FLOAT);
866         if(tnl->render_inputs & _TNL_BIT_POINTSIZE)
867                 CONFIGURE_AOS(VB->PointSizePtr, 0, i_pointsize, AOS_FORMAT_FLOAT);
868
869         r300->state.aos_count=count;
870
871         if (RADEON_DEBUG & DEBUG_STATE)
872                 fprintf(stderr, "aos_count=%d\n", count);
873
874         if(count>R300_MAX_AOS_ARRAYS){
875                 fprintf(stderr, "Aieee ! AOS array count exceeded !\n");
876                 exit(-1);
877                 }
878
879         /* Implement AOS */
880
881         /* setup INPUT_ROUTE */
882         R300_STATECHANGE(r300, vir[0]);
883         for(i=0;i+1<count;i+=2){
884                 dw=(r300->state.aos[i].ncomponents-1)
885                 | ((r300->state.aos[i].reg)<<8)
886                 | (r300->state.aos[i].format<<14)
887                 | (((r300->state.aos[i+1].ncomponents-1)
888                 | ((r300->state.aos[i+1].reg)<<8)
889                 | (r300->state.aos[i+1].format<<14))<<16);
890
891                 if(i+2==count){
892                         dw|=(1<<(13+16));
893                         }
894                 r300->hw.vir[0].cmd[R300_VIR_CNTL_0+(i>>1)]=dw;
895                 }
896         if(count & 1){
897                 dw=(r300->state.aos[count-1].ncomponents-1)
898                 | (r300->state.aos[count-1].format<<14)
899                 | ((r300->state.aos[count-1].reg)<<8)
900                 | (1<<13);
901                 r300->hw.vir[0].cmd[R300_VIR_CNTL_0+(count>>1)]=dw;
902                 //fprintf(stderr, "vir0 dw=%08x\n", dw);
903                 }
904         /* Set the rest of INPUT_ROUTE_0 to 0 */
905         //for(i=((count+1)>>1); i<8; i++)r300->hw.vir[0].cmd[R300_VIR_CNTL_0+i]=(0x0);
906         ((drm_r300_cmd_header_t*)r300->hw.vir[0].cmd)->unchecked_state.count = (count+1)>>1;
907
908
909         /* Mesa assumes that all missing components are from (0, 0, 0, 1) */
910         #define ALL_COMPONENTS ((R300_INPUT_ROUTE_SELECT_X<<R300_INPUT_ROUTE_X_SHIFT) \
911                 | (R300_INPUT_ROUTE_SELECT_Y<<R300_INPUT_ROUTE_Y_SHIFT) \
912                 | (R300_INPUT_ROUTE_SELECT_Z<<R300_INPUT_ROUTE_Z_SHIFT) \
913                 | (R300_INPUT_ROUTE_SELECT_W<<R300_INPUT_ROUTE_W_SHIFT))
914
915         #define ALL_DEFAULT ((R300_INPUT_ROUTE_SELECT_ZERO<<R300_INPUT_ROUTE_X_SHIFT) \
916                 | (R300_INPUT_ROUTE_SELECT_ZERO<<R300_INPUT_ROUTE_Y_SHIFT) \
917                 | (R300_INPUT_ROUTE_SELECT_ZERO<<R300_INPUT_ROUTE_Z_SHIFT) \
918                 | (R300_INPUT_ROUTE_SELECT_ONE<<R300_INPUT_ROUTE_W_SHIFT))
919
920         R300_STATECHANGE(r300, vir[1]);
921
922         for(i=0;i+1<count;i+=2){
923                 /* do i first.. */
924                 mask=(1<<(r300->state.aos[i].ncomponents*3))-1;
925                 dw=(ALL_COMPONENTS & mask)
926                 | (ALL_DEFAULT & ~mask)
927                 | R300_INPUT_ROUTE_ENABLE;
928
929                 /* i+1 */
930                 mask=(1<<(r300->state.aos[i+1].ncomponents*3))-1;
931                 dw|=(
932                 (ALL_COMPONENTS & mask)
933                 | (ALL_DEFAULT & ~mask)
934                 | R300_INPUT_ROUTE_ENABLE
935                 )<<16;
936
937                 r300->hw.vir[1].cmd[R300_VIR_CNTL_0+(i>>1)]=dw;
938                 }
939         if(count & 1){
940                 mask=(1<<(r300->state.aos[count-1].ncomponents*3))-1;
941                 dw=(ALL_COMPONENTS & mask)
942                 | (ALL_DEFAULT & ~mask)
943                 | R300_INPUT_ROUTE_ENABLE;
944                 r300->hw.vir[1].cmd[R300_VIR_CNTL_0+(count>>1)]=dw;
945                 //fprintf(stderr, "vir1 dw=%08x\n", dw);
946                 }
947         /* Set the rest of INPUT_ROUTE_1 to 0 */
948         //for(i=((count+1)>>1); i<8; i++)r300->hw.vir[1].cmd[R300_VIR_CNTL_0+i]=0x0;
949         ((drm_r300_cmd_header_t*)r300->hw.vir[1].cmd)->unchecked_state.count = (count+1)>>1;
950
951         /* Set up input_cntl */
952
953         R300_STATECHANGE(r300, vic);
954         r300->hw.vic.cmd[R300_VIC_CNTL_0]=0x5555;  /* Hard coded value, no idea what it means */
955
956         r300->hw.vic.cmd[R300_VIC_CNTL_1]=R300_INPUT_CNTL_POS
957                                         | R300_INPUT_CNTL_COLOR;
958
959         for(i=0;i < ctx->Const.MaxTextureUnits;i++)
960                 if(ctx->Texture.Unit[i].Enabled)
961                         r300->hw.vic.cmd[R300_VIC_CNTL_1]|=(R300_INPUT_CNTL_TC0<<i);
962
963         /* Stage 3: VAP output */
964         R300_STATECHANGE(r300, vof);
965         r300->hw.vof.cmd[R300_VOF_CNTL_0]=R300_VAP_OUTPUT_VTX_FMT_0__POS_PRESENT
966                                         | R300_VAP_OUTPUT_VTX_FMT_0__COLOR_PRESENT;
967
968         r300->hw.vof.cmd[R300_VOF_CNTL_1]=0;
969         for(i=0;i < ctx->Const.MaxTextureUnits;i++)
970                 if(ctx->Texture.Unit[i].Enabled)
971                         r300->hw.vof.cmd[R300_VOF_CNTL_1]|=(4<<(3*i));
972
973 }
974
975 static r300TexObj default_tex_obj={
976         filter:R300_TX_MAG_FILTER_LINEAR | R300_TX_MIN_FILTER_LINEAR,
977         pitch: 0x8000,
978         size: (0xff << R300_TX_WIDTHMASK_SHIFT)
979               | (0xff << R300_TX_HEIGHTMASK_SHIFT)
980               | (0x8 << R300_TX_SIZE_SHIFT),
981         format: 0x88a0c,
982         offset: 0x0,
983         unknown4: 0x0,
984         unknown5: 0x0
985         };
986
987         /* there is probably a system to these value, but, for now,
988            we just try by hand */
989
990 static int inline translate_src(int src)
991 {
992         switch (src) {
993         case GL_TEXTURE:
994                 return 1;
995                 break;
996         case GL_CONSTANT:
997                 return 2;
998                 break;
999         case GL_PRIMARY_COLOR:
1000                 return 3;
1001                 break;
1002         case GL_PREVIOUS:
1003                 return 4;
1004                 break;
1005         case GL_ZERO:
1006                 return 5;
1007                 break;
1008         case GL_ONE:
1009                 return 6;
1010                 break;
1011         default:
1012                 return 0;
1013         }
1014 }
1015
1016 /* r300 doesnt handle GL_CLAMP and GL_MIRROR_CLAMP_EXT correctly when filter is NEAREST.
1017  * Since texwrap produces same results for GL_CLAMP and GL_CLAMP_TO_EDGE we use them instead.
1018  * We need to recalculate wrap modes whenever filter mode is changed because someone might do:
1019  * glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
1020  * glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
1021  * glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
1022  * Since r300 completely ignores R300_TX_CLAMP when either min or mag is nearest it cant handle
1023  * combinations where only one of them is nearest.
1024  */
1025 static unsigned long gen_fixed_filter(unsigned long f)
1026 {
1027         unsigned long mag, min, needs_fixing=0;
1028         //return f;
1029         
1030         /* We ignore MIRROR bit so we dont have to do everything twice */
1031         if((f & ((7-1) << R300_TX_WRAP_S_SHIFT)) == (R300_TX_CLAMP << R300_TX_WRAP_S_SHIFT)){
1032                 needs_fixing |= 1;
1033         }
1034         if((f & ((7-1) << R300_TX_WRAP_T_SHIFT)) == (R300_TX_CLAMP << R300_TX_WRAP_T_SHIFT)){
1035                 needs_fixing |= 2;
1036         }
1037         if((f & ((7-1) << R300_TX_WRAP_Q_SHIFT)) == (R300_TX_CLAMP << R300_TX_WRAP_Q_SHIFT)){
1038                 needs_fixing |= 4;
1039         }
1040         
1041         if(!needs_fixing)
1042                 return f;
1043         
1044         mag=f & R300_TX_MAG_FILTER_MASK;
1045         min=f & R300_TX_MIN_FILTER_MASK;
1046         
1047         /* TODO: Check for anisto filters too */
1048         if((mag != R300_TX_MAG_FILTER_NEAREST) && (min != R300_TX_MIN_FILTER_NEAREST))
1049                 return f;
1050         
1051         /* r300 cant handle these modes hence we force nearest to linear */
1052         if((mag == R300_TX_MAG_FILTER_NEAREST) && (min != R300_TX_MIN_FILTER_NEAREST)){
1053                 f &= ~R300_TX_MAG_FILTER_NEAREST;
1054                 f |= R300_TX_MAG_FILTER_LINEAR;
1055                 return f;
1056         }
1057         
1058         if((min == R300_TX_MIN_FILTER_NEAREST) && (mag != R300_TX_MAG_FILTER_NEAREST)){
1059                 f &= ~R300_TX_MIN_FILTER_NEAREST;
1060                 f |= R300_TX_MIN_FILTER_LINEAR;
1061                 return f;
1062         }
1063         
1064         /* Both are nearest */
1065         if(needs_fixing & 1){
1066                 f &= ~((7-1) << R300_TX_WRAP_S_SHIFT);
1067                 f |= R300_TX_CLAMP_TO_EDGE << R300_TX_WRAP_S_SHIFT;
1068         }
1069         if(needs_fixing & 2){
1070                 f &= ~((7-1) << R300_TX_WRAP_T_SHIFT);
1071                 f |= R300_TX_CLAMP_TO_EDGE << R300_TX_WRAP_T_SHIFT;
1072         }
1073         if(needs_fixing & 4){
1074                 f &= ~((7-1) << R300_TX_WRAP_Q_SHIFT);
1075                 f |= R300_TX_CLAMP_TO_EDGE << R300_TX_WRAP_Q_SHIFT;
1076         }
1077         return f;
1078 }
1079
1080 void r300_setup_textures(GLcontext *ctx)
1081 {
1082         int i, mtu;
1083         struct r300_tex_obj *t;
1084         r300ContextPtr r300 = R300_CONTEXT(ctx);
1085         int max_texture_unit=-1; /* -1 translates into no setup costs for fields */
1086         struct gl_texture_unit *texUnit;
1087
1088         R300_STATECHANGE(r300, txe);
1089         R300_STATECHANGE(r300, tex.filter);
1090         R300_STATECHANGE(r300, tex.unknown1);
1091         R300_STATECHANGE(r300, tex.size);
1092         R300_STATECHANGE(r300, tex.format);
1093         R300_STATECHANGE(r300, tex.offset);
1094         R300_STATECHANGE(r300, tex.unknown4);
1095         R300_STATECHANGE(r300, tex.unknown5);
1096         //R300_STATECHANGE(r300, tex.border_color);
1097
1098         r300->state.texture.tc_count=0;
1099
1100         r300->hw.txe.cmd[R300_TXE_ENABLE]=0x0;
1101
1102         mtu = r300->radeon.glCtx->Const.MaxTextureUnits;
1103         if (RADEON_DEBUG & DEBUG_STATE)
1104                 fprintf(stderr, "mtu=%d\n", mtu);
1105
1106         if(mtu>R300_MAX_TEXTURE_UNITS){
1107                 fprintf(stderr, "Aiiee ! mtu=%d is greater than R300_MAX_TEXTURE_UNITS=%d\n",
1108                         mtu, R300_MAX_TEXTURE_UNITS);
1109                 exit(-1);
1110                 }
1111         for(i=0;i<mtu;i++){
1112                 if(ctx->Texture.Unit[i].Enabled){
1113                         t=r300->state.texture.unit[i].texobj;
1114                         //fprintf(stderr, "format=%08x\n", r300->state.texture.unit[i].format);
1115                         r300->state.texture.tc_count++;
1116                         if(t==NULL){
1117                                 fprintf(stderr, "Texture unit %d enabled, but corresponding texobj is NULL, using default object.\n", i);
1118                                 //exit(-1);
1119                                 t=&default_tex_obj;
1120                                 }
1121                         //fprintf(stderr, "t->format=%08x\n", t->format);
1122                         if (RADEON_DEBUG & DEBUG_STATE)
1123                                 fprintf(stderr, "Activating texture unit %d\n", i);
1124                         max_texture_unit=i;
1125                         r300->hw.txe.cmd[R300_TXE_ENABLE]|=(1<<i);
1126
1127                         r300->hw.tex.filter.cmd[R300_TEX_VALUE_0+i]=gen_fixed_filter(t->filter);
1128                         /* No idea why linear filtered textures shake when puting random data */
1129                         /*r300->hw.tex.unknown1.cmd[R300_TEX_VALUE_0+i]=(rand()%0xffffffff) & (~0x1fff);*/
1130                         r300->hw.tex.size.cmd[R300_TEX_VALUE_0+i]=t->size;
1131                         r300->hw.tex.format.cmd[R300_TEX_VALUE_0+i]=t->format;
1132                         //fprintf(stderr, "t->format=%08x\n", t->format);
1133                         r300->hw.tex.offset.cmd[R300_TEX_VALUE_0+i]=r300->radeon.radeonScreen->fbLocation+t->offset;
1134                         r300->hw.tex.unknown4.cmd[R300_TEX_VALUE_0+i]=0x0;
1135                         r300->hw.tex.unknown5.cmd[R300_TEX_VALUE_0+i]=0x0;
1136                         //r300->hw.tex.border_color.cmd[R300_TEX_VALUE_0+i]=t->pp_border_color;
1137                         }
1138                 }
1139         ((drm_r300_cmd_header_t*)r300->hw.tex.filter.cmd)->unchecked_state.count = max_texture_unit+1;
1140         ((drm_r300_cmd_header_t*)r300->hw.tex.unknown1.cmd)->unchecked_state.count = max_texture_unit+1;
1141         ((drm_r300_cmd_header_t*)r300->hw.tex.size.cmd)->unchecked_state.count = max_texture_unit+1;
1142         ((drm_r300_cmd_header_t*)r300->hw.tex.format.cmd)->unchecked_state.count = max_texture_unit+1;
1143         ((drm_r300_cmd_header_t*)r300->hw.tex.offset.cmd)->unchecked_state.count = max_texture_unit+1;
1144         ((drm_r300_cmd_header_t*)r300->hw.tex.unknown4.cmd)->unchecked_state.count = max_texture_unit+1;
1145         ((drm_r300_cmd_header_t*)r300->hw.tex.unknown5.cmd)->unchecked_state.count = max_texture_unit+1;
1146         //((drm_r300_cmd_header_t*)r300->hw.tex.border_color.cmd)->unchecked_state.count = max_texture_unit+1;
1147
1148         if (RADEON_DEBUG & DEBUG_STATE)
1149                 fprintf(stderr, "TX_ENABLE: %08x  max_texture_unit=%d\n", r300->hw.txe.cmd[R300_TXE_ENABLE], max_texture_unit);
1150 }
1151
1152 void r300_setup_rs_unit(GLcontext *ctx)
1153 {
1154         r300ContextPtr r300 = R300_CONTEXT(ctx);
1155         int i;
1156
1157         /* This needs to be rewritten - it is a hack at best */
1158
1159         R300_STATECHANGE(r300, ri);
1160         R300_STATECHANGE(r300, rc);
1161         R300_STATECHANGE(r300, rr);
1162
1163         for(i = 1; i <= 8; ++i)
1164                 r300->hw.ri.cmd[i] = 0x00d10000;
1165         r300->hw.ri.cmd[R300_RI_INTERP_1] |= R300_RS_INTERP_1_UNKNOWN;
1166         r300->hw.ri.cmd[R300_RI_INTERP_2] |= R300_RS_INTERP_2_UNKNOWN;
1167         r300->hw.ri.cmd[R300_RI_INTERP_3] |= R300_RS_INTERP_3_UNKNOWN;
1168
1169         #if 1
1170         for(i = 2; i <= 8; ++i)
1171                 r300->hw.ri.cmd[i] |= 4;
1172         #endif
1173
1174         for(i = 1; i <= 8; ++i)
1175                 r300->hw.rr.cmd[i] = 0;
1176         /* textures enabled ? */
1177         if(r300->state.texture.tc_count>0){
1178
1179                 /* This code only really works with one set of texture coordinates */
1180
1181                 /* The second constant is needed to get glxgears display anything .. */
1182                 r300->hw.rc.cmd[1] = R300_RS_CNTL_0_UNKNOWN_7
1183                                 | R300_RS_CNTL_0_UNKNOWN_18
1184                                 | (r300->state.texture.tc_count<<R300_RS_CNTL_TC_CNT_SHIFT);
1185                 r300->hw.rc.cmd[2] = 0xc0;
1186
1187
1188                 ((drm_r300_cmd_header_t*)r300->hw.rr.cmd)->unchecked_state.count = 1;
1189                 r300->hw.rr.cmd[R300_RR_ROUTE_0] = 0x24008;
1190
1191                 } else {
1192
1193                 /* The second constant is needed to get glxgears display anything .. */
1194                 r300->hw.rc.cmd[1] = R300_RS_CNTL_0_UNKNOWN_7 | R300_RS_CNTL_0_UNKNOWN_18;
1195                 r300->hw.rc.cmd[2] = 0;
1196
1197                 ((drm_r300_cmd_header_t*)r300->hw.rr.cmd)->unchecked_state.count = 1;
1198                 r300->hw.rr.cmd[R300_RR_ROUTE_0] = 0x4000;
1199
1200                 }
1201 }
1202
1203 #define vpucount(ptr) (((drm_r300_cmd_header_t*)(ptr))->vpu.count)
1204
1205 #define bump_vpu_count(ptr, new_count)   do{\
1206         drm_r300_cmd_header_t* _p=((drm_r300_cmd_header_t*)(ptr));\
1207         int _nc=(new_count)/4; \
1208         if(_nc>_p->vpu.count)_p->vpu.count=_nc;\
1209         }while(0)
1210
1211 void static inline setup_vertex_shader_fragment(r300ContextPtr r300, int dest, struct r300_vertex_shader_fragment *vsf)
1212 {
1213         int i;
1214
1215         if(vsf->length==0)return;
1216
1217         if(vsf->length & 0x3){
1218                 fprintf(stderr,"VERTEX_SHADER_FRAGMENT must have length divisible by 4\n");
1219                 exit(-1);
1220                 }
1221
1222         switch((dest>>8) & 0xf){
1223         case 0:
1224                 R300_STATECHANGE(r300, vpi);
1225                 for(i=0;i<vsf->length;i++)
1226                         r300->hw.vpi.cmd[R300_VPI_INSTR_0+i+4*(dest & 0xff)]=(vsf->body.d[i]);
1227                 bump_vpu_count(r300->hw.vpi.cmd, vsf->length+4*(dest & 0xff));
1228                 break;
1229
1230         case 2:
1231                 R300_STATECHANGE(r300, vpp);
1232                 for(i=0;i<vsf->length;i++)
1233                         r300->hw.vpp.cmd[R300_VPP_PARAM_0+i+4*(dest & 0xff)]=(vsf->body.d[i]);
1234                 bump_vpu_count(r300->hw.vpp.cmd, vsf->length+4*(dest & 0xff));
1235                 break;
1236         case 4:
1237                 R300_STATECHANGE(r300, vps);
1238                 for(i=0;i<vsf->length;i++)
1239                         r300->hw.vps.cmd[1+i+4*(dest & 0xff)]=(vsf->body.d[i]);
1240                 bump_vpu_count(r300->hw.vps.cmd, vsf->length+4*(dest & 0xff));
1241                 break;
1242         default:
1243                 fprintf(stderr, "%s:%s don't know how to handle dest %04x\n", __FILE__, __FUNCTION__, dest);
1244                 exit(-1);
1245         }
1246 }
1247
1248
1249 void r300SetupVertexShader(r300ContextPtr rmesa)
1250 {
1251         GLcontext* ctx = rmesa->radeon.glCtx;
1252
1253         /* Reset state, in case we don't use something */
1254         ((drm_r300_cmd_header_t*)rmesa->hw.vpp.cmd)->vpu.count = 0;
1255         ((drm_r300_cmd_header_t*)rmesa->hw.vpi.cmd)->vpu.count = 0;
1256         ((drm_r300_cmd_header_t*)rmesa->hw.vps.cmd)->vpu.count = 0;
1257
1258
1259 /* This needs to be replaced by vertex shader generation code */
1260
1261
1262         /* textures enabled ? */
1263         if(rmesa->state.texture.tc_count>0){
1264                 rmesa->state.vertex_shader=SINGLE_TEXTURE_VERTEX_SHADER;
1265                 } else {
1266                 rmesa->state.vertex_shader=FLAT_COLOR_VERTEX_SHADER;
1267                 }
1268
1269
1270         rmesa->state.vertex_shader.matrix[0].length=16;
1271         memcpy(rmesa->state.vertex_shader.matrix[0].body.f, ctx->_ModelProjectMatrix.m, 16*4);
1272
1273         setup_vertex_shader_fragment(rmesa, VSF_DEST_PROGRAM, &(rmesa->state.vertex_shader.program));
1274
1275         setup_vertex_shader_fragment(rmesa, VSF_DEST_MATRIX0, &(rmesa->state.vertex_shader.matrix[0]));
1276         #if 0
1277         setup_vertex_shader_fragment(rmesa, VSF_DEST_MATRIX1, &(rmesa->state.vertex_shader.matrix[0]));
1278         setup_vertex_shader_fragment(rmesa, VSF_DEST_MATRIX2, &(rmesa->state.vertex_shader.matrix[0]));
1279
1280         setup_vertex_shader_fragment(rmesa, VSF_DEST_VECTOR0, &(rmesa->state.vertex_shader.vector[0]));
1281         setup_vertex_shader_fragment(rmesa, VSF_DEST_VECTOR1, &(rmesa->state.vertex_shader.vector[1]));
1282         #endif
1283
1284         #if 0
1285         setup_vertex_shader_fragment(rmesa, VSF_DEST_UNKNOWN1, &(rmesa->state.vertex_shader.unknown1));
1286         setup_vertex_shader_fragment(rmesa, VSF_DEST_UNKNOWN2, &(rmesa->state.vertex_shader.unknown2));
1287         #endif
1288
1289         R300_STATECHANGE(rmesa, pvs);
1290         rmesa->hw.pvs.cmd[R300_PVS_CNTL_1]=(rmesa->state.vertex_shader.program_start << R300_PVS_CNTL_1_PROGRAM_START_SHIFT)
1291                 | (rmesa->state.vertex_shader.unknown_ptr1 << R300_PVS_CNTL_1_UNKNOWN_SHIFT)
1292                 | (rmesa->state.vertex_shader.program_end << R300_PVS_CNTL_1_PROGRAM_END_SHIFT);
1293         rmesa->hw.pvs.cmd[R300_PVS_CNTL_2]=(rmesa->state.vertex_shader.param_offset << R300_PVS_CNTL_2_PARAM_OFFSET_SHIFT)
1294                 | (rmesa->state.vertex_shader.param_count << R300_PVS_CNTL_2_PARAM_COUNT_SHIFT);
1295         rmesa->hw.pvs.cmd[R300_PVS_CNTL_3]=(rmesa->state.vertex_shader.unknown_ptr2 << R300_PVS_CNTL_3_PROGRAM_UNKNOWN_SHIFT)
1296         | (rmesa->state.vertex_shader.unknown_ptr3 << 0);
1297
1298         /* This is done for vertex shader fragments, but also needs to be done for vap_pvs,
1299         so I leave it as a reminder */
1300         #if 0
1301         reg_start(R300_VAP_PVS_WAITIDLE,0);
1302                 e32(0x00000000);
1303         #endif
1304 }
1305
1306 void r300SetupVertexProgram(r300ContextPtr rmesa)
1307 {
1308         GLcontext* ctx = rmesa->radeon.glCtx;
1309
1310         /* Reset state, in case we don't use something */
1311         ((drm_r300_cmd_header_t*)rmesa->hw.vpp.cmd)->vpu.count = 0;
1312         ((drm_r300_cmd_header_t*)rmesa->hw.vpi.cmd)->vpu.count = 0;
1313         ((drm_r300_cmd_header_t*)rmesa->hw.vps.cmd)->vpu.count = 0;
1314
1315 #if 0
1316 /* This needs to be replaced by vertex shader generation code */
1317
1318
1319         /* textures enabled ? */
1320         if(rmesa->state.texture.tc_count>0){
1321                 rmesa->state.vertex_shader=SINGLE_TEXTURE_VERTEX_SHADER;
1322                 } else {
1323                 rmesa->state.vertex_shader=FLAT_COLOR_VERTEX_SHADER;
1324                 }
1325
1326
1327         rmesa->state.vertex_shader.matrix[0].length=16;
1328         memcpy(rmesa->state.vertex_shader.matrix[0].body.f, ctx->_ModelProjectMatrix.m, 16*4);
1329 #endif
1330         
1331         setup_vertex_shader_fragment(rmesa, VSF_DEST_PROGRAM, &(rmesa->current_vp->program));
1332
1333         setup_vertex_shader_fragment(rmesa, VSF_DEST_MATRIX0, &(rmesa->current_vp->params));
1334         
1335         #if 0
1336         setup_vertex_shader_fragment(rmesa, VSF_DEST_UNKNOWN1, &(rmesa->state.vertex_shader.unknown1));
1337         setup_vertex_shader_fragment(rmesa, VSF_DEST_UNKNOWN2, &(rmesa->state.vertex_shader.unknown2));
1338         #endif
1339
1340         R300_STATECHANGE(rmesa, pvs);
1341         rmesa->hw.pvs.cmd[R300_PVS_CNTL_1]=(0 << R300_PVS_CNTL_1_PROGRAM_START_SHIFT)
1342                 | (rmesa->state.vertex_shader.unknown_ptr1 << R300_PVS_CNTL_1_UNKNOWN_SHIFT)
1343                 | (rmesa->current_vp->program.length/4 << R300_PVS_CNTL_1_PROGRAM_END_SHIFT);
1344         rmesa->hw.pvs.cmd[R300_PVS_CNTL_2]=(0 << R300_PVS_CNTL_2_PARAM_OFFSET_SHIFT)
1345                 | (rmesa->current_vp->params.length/4 << R300_PVS_CNTL_2_PARAM_COUNT_SHIFT);
1346         rmesa->hw.pvs.cmd[R300_PVS_CNTL_3]=(0/*rmesa->state.vertex_shader.unknown_ptr2*/ << R300_PVS_CNTL_3_PROGRAM_UNKNOWN_SHIFT)
1347         | (rmesa->current_vp->program.length/4/*rmesa->state.vertex_shader.unknown_ptr3*/ << 0);
1348
1349         /* This is done for vertex shader fragments, but also needs to be done for vap_pvs,
1350         so I leave it as a reminder */
1351         #if 0
1352         reg_start(R300_VAP_PVS_WAITIDLE,0);
1353                 e32(0x00000000);
1354         #endif
1355 }
1356
1357 void r300SetupPixelShader(r300ContextPtr rmesa)
1358 {
1359 int i,k;
1360
1361         /* This needs to be replaced by pixel shader generation code */
1362
1363         /* textures enabled ? */
1364         if(rmesa->state.texture.tc_count>0){
1365                 rmesa->state.pixel_shader=SINGLE_TEXTURE_PIXEL_SHADER;
1366                 } else {
1367                 rmesa->state.pixel_shader=FLAT_COLOR_PIXEL_SHADER;
1368                 }
1369
1370         R300_STATECHANGE(rmesa, fpt);
1371         for(i=0;i<rmesa->state.pixel_shader.program.tex.length;i++)
1372                 rmesa->hw.fpt.cmd[R300_FPT_INSTR_0+i]=rmesa->state.pixel_shader.program.tex.inst[i];
1373         rmesa->hw.fpt.cmd[R300_FPT_CMD_0]=cmducs(R300_PFS_TEXI_0, rmesa->state.pixel_shader.program.tex.length);
1374
1375         #define OUTPUT_FIELD(st, reg, field)  \
1376                 R300_STATECHANGE(rmesa, st); \
1377                 for(i=0;i<rmesa->state.pixel_shader.program.alu.length;i++) \
1378                         rmesa->hw.st.cmd[R300_FPI_INSTR_0+i]=rmesa->state.pixel_shader.program.alu.inst[i].field;\
1379                 rmesa->hw.st.cmd[R300_FPI_CMD_0]=cmducs(reg, rmesa->state.pixel_shader.program.alu.length);
1380
1381         OUTPUT_FIELD(fpi[0], R300_PFS_INSTR0_0, inst0);
1382         OUTPUT_FIELD(fpi[1], R300_PFS_INSTR1_0, inst1);
1383         OUTPUT_FIELD(fpi[2], R300_PFS_INSTR2_0, inst2);
1384         OUTPUT_FIELD(fpi[3], R300_PFS_INSTR3_0, inst3);
1385         #undef OUTPUT_FIELD
1386
1387         R300_STATECHANGE(rmesa, fp);
1388         for(i=0;i<4;i++){
1389                 rmesa->hw.fp.cmd[R300_FP_NODE0+i]=
1390                 (rmesa->state.pixel_shader.program.node[i].alu_offset << R300_PFS_NODE_ALU_OFFSET_SHIFT)
1391                 | (rmesa->state.pixel_shader.program.node[i].alu_end  << R300_PFS_NODE_ALU_END_SHIFT)
1392                 | (rmesa->state.pixel_shader.program.node[i].tex_offset << R300_PFS_NODE_TEX_OFFSET_SHIFT)
1393                 | (rmesa->state.pixel_shader.program.node[i].tex_end  << R300_PFS_NODE_TEX_END_SHIFT)
1394                 | ( (i==3) ? R300_PFS_NODE_LAST_NODE : 0);
1395                 }
1396
1397                 /*  PFS_CNTL_0 */
1398         rmesa->hw.fp.cmd[R300_FP_CNTL0]=
1399                 (rmesa->state.pixel_shader.program.active_nodes-1)
1400                 | (rmesa->state.pixel_shader.program.first_node_has_tex<<3);
1401                 /* PFS_CNTL_1 */
1402         rmesa->hw.fp.cmd[R300_FP_CNTL1]=rmesa->state.pixel_shader.program.temp_register_count;
1403                 /* PFS_CNTL_2 */
1404         rmesa->hw.fp.cmd[R300_FP_CNTL2]=
1405                 (rmesa->state.pixel_shader.program.alu_offset << R300_PFS_CNTL_ALU_OFFSET_SHIFT)
1406                 | (rmesa->state.pixel_shader.program.alu_end << R300_PFS_CNTL_ALU_END_SHIFT)
1407                 | (rmesa->state.pixel_shader.program.tex_offset << R300_PFS_CNTL_TEX_OFFSET_SHIFT)
1408                 | (rmesa->state.pixel_shader.program.tex_end << R300_PFS_CNTL_TEX_END_SHIFT);
1409
1410         R300_STATECHANGE(rmesa, fpp);
1411         for(i=0;i<rmesa->state.pixel_shader.param_length;i++){
1412                 rmesa->hw.fpp.cmd[R300_FPP_PARAM_0+4*i+0]=r300PackFloat32(rmesa->state.pixel_shader.param[i].x);
1413                 rmesa->hw.fpp.cmd[R300_FPP_PARAM_0+4*i+1]=r300PackFloat32(rmesa->state.pixel_shader.param[i].y);
1414                 rmesa->hw.fpp.cmd[R300_FPP_PARAM_0+4*i+2]=r300PackFloat32(rmesa->state.pixel_shader.param[i].z);
1415                 rmesa->hw.fpp.cmd[R300_FPP_PARAM_0+4*i+3]=r300PackFloat32(rmesa->state.pixel_shader.param[i].w);
1416                 }
1417         rmesa->hw.fpp.cmd[R300_FPP_CMD_0]=cmducs(R300_PFS_PARAM_0_X, rmesa->state.pixel_shader.param_length);
1418
1419 }
1420
1421 /**
1422  * Called by Mesa after an internal state update.
1423  */
1424 static void r300InvalidateState(GLcontext * ctx, GLuint new_state)
1425 {
1426         r300ContextPtr r300 = R300_CONTEXT(ctx);
1427
1428         _swrast_InvalidateState(ctx, new_state);
1429         _swsetup_InvalidateState(ctx, new_state);
1430         _ac_InvalidateState(ctx, new_state);
1431         _tnl_InvalidateState(ctx, new_state);
1432         _ae_invalidate_state(ctx, new_state);
1433
1434         /* Go inefficiency! */
1435         r300ResetHwState(r300);
1436 }
1437
1438
1439 /**
1440  * Completely recalculates hardware state based on the Mesa state.
1441  */
1442 void r300ResetHwState(r300ContextPtr r300)
1443 {
1444         GLcontext* ctx = r300->radeon.glCtx;
1445         int i;
1446
1447         if (RADEON_DEBUG & DEBUG_STATE)
1448                 fprintf(stderr, "%s\n", __FUNCTION__);
1449
1450                 /* This is a place to initialize registers which
1451                    have bitfields accessed by different functions
1452                    and not all bits are used */
1453         #if 0
1454         r300->hw.zs.cmd[R300_ZS_CNTL_0] = 0;
1455         r300->hw.zs.cmd[R300_ZS_CNTL_1] = 0;
1456         r300->hw.zs.cmd[R300_ZS_CNTL_2] = 0xffff00;
1457         #endif
1458
1459                 /* go and compute register values from GL state */
1460
1461         r300UpdateWindow(ctx);
1462
1463         r300ColorMask(ctx,
1464                 ctx->Color.ColorMask[RCOMP],
1465                 ctx->Color.ColorMask[GCOMP],
1466                 ctx->Color.ColorMask[BCOMP],
1467                 ctx->Color.ColorMask[ACOMP]);
1468
1469         r300Enable(ctx, GL_DEPTH_TEST, ctx->Depth.Test);
1470         r300DepthMask(ctx, ctx->Depth.Mask);
1471         r300DepthFunc(ctx, ctx->Depth.Func);
1472
1473         r300UpdateCulling(ctx);
1474
1475         r300_setup_routing(ctx, GL_TRUE);
1476
1477         r300UpdateTextureState(ctx);
1478         r300_setup_textures(ctx);
1479         r300_setup_rs_unit(ctx);
1480
1481         r300SetupVertexShader(r300);
1482         r300SetupPixelShader(r300);
1483
1484         r300_set_blend_state(ctx);
1485         r300AlphaFunc(ctx, ctx->Color.AlphaFunc, ctx->Color.AlphaRef);
1486
1487                 /* Initialize magic registers
1488                  TODO : learn what they really do, or get rid of
1489                  those we don't have to touch */
1490         r300->hw.unk2080.cmd[1] = 0x0030045A;
1491
1492         r300->hw.vte.cmd[1] = R300_VPORT_X_SCALE_ENA
1493                                 | R300_VPORT_X_OFFSET_ENA
1494                                 | R300_VPORT_Y_SCALE_ENA
1495                                 | R300_VPORT_Y_OFFSET_ENA
1496                                 | R300_VPORT_Z_SCALE_ENA
1497                                 | R300_VPORT_Z_OFFSET_ENA
1498                                 | R300_VTX_W0_FMT;
1499         r300->hw.vte.cmd[2] = 0x00000008;
1500
1501         r300->hw.unk2134.cmd[1] = 0x00FFFFFF;
1502         r300->hw.unk2134.cmd[2] = 0x00000000;
1503
1504         r300->hw.unk2140.cmd[1] = 0x00000000;
1505
1506         #if 0 /* Done in setup routing */
1507         ((drm_r300_cmd_header_t*)r300->hw.vir[0].cmd)->unchecked_state.count = 1;
1508         r300->hw.vir[0].cmd[1] = 0x21030003;
1509
1510         ((drm_r300_cmd_header_t*)r300->hw.vir[1].cmd)->unchecked_state.count = 1;
1511         r300->hw.vir[1].cmd[1] = 0xF688F688;
1512
1513         r300->hw.vic.cmd[R300_VIR_CNTL_0] = 0x00000001;
1514         r300->hw.vic.cmd[R300_VIR_CNTL_1] = 0x00000405;
1515         #endif
1516
1517         r300->hw.unk21DC.cmd[1] = 0xAAAAAAAA;
1518
1519         r300->hw.unk221C.cmd[1] = R300_221C_NORMAL;
1520
1521         r300->hw.unk2220.cmd[1] = r300PackFloat32(1.0);
1522         r300->hw.unk2220.cmd[2] = r300PackFloat32(1.0);
1523         r300->hw.unk2220.cmd[3] = r300PackFloat32(1.0);
1524         r300->hw.unk2220.cmd[4] = r300PackFloat32(1.0);
1525
1526         if (GET_CHIP(r300->radeon.radeonScreen) == RADEON_CHIP_R300)
1527                 r300->hw.unk2288.cmd[1] = R300_2288_R300;
1528         else
1529                 r300->hw.unk2288.cmd[1] = R300_2288_RV350;
1530
1531         #if 0
1532         r300->hw.vof.cmd[R300_VOF_CNTL_0] = R300_VAP_OUTPUT_VTX_FMT_0__POS_PRESENT
1533                                 | R300_VAP_OUTPUT_VTX_FMT_0__COLOR_PRESENT;
1534         r300->hw.vof.cmd[R300_VOF_CNTL_1] = 0; /* no textures */
1535
1536
1537         r300->hw.pvs.cmd[R300_PVS_CNTL_1] = 0;
1538         r300->hw.pvs.cmd[R300_PVS_CNTL_2] = 0;
1539         r300->hw.pvs.cmd[R300_PVS_CNTL_3] = 0;
1540         #endif
1541
1542         r300->hw.gb_enable.cmd[1] = R300_GB_POINT_STUFF_ENABLE
1543                 | R300_GB_LINE_STUFF_ENABLE
1544                 | R300_GB_TRIANGLE_STUFF_ENABLE;
1545
1546         r300->hw.gb_misc.cmd[R300_GB_MISC_MSPOS_0] = 0x66666666;
1547         r300->hw.gb_misc.cmd[R300_GB_MISC_MSPOS_1] = 0x06666666;
1548         if (GET_CHIP(r300->radeon.radeonScreen) == RADEON_CHIP_R300)
1549                 r300->hw.gb_misc.cmd[R300_GB_MISC_TILE_CONFIG] = R300_GB_TILE_ENABLE
1550                                                         | R300_GB_TILE_PIPE_COUNT_R300
1551                                                         | R300_GB_TILE_SIZE_16;
1552         else
1553                 r300->hw.gb_misc.cmd[R300_GB_MISC_TILE_CONFIG] = R300_GB_TILE_ENABLE
1554                                                         | R300_GB_TILE_PIPE_COUNT_RV300
1555                                                         | R300_GB_TILE_SIZE_16;
1556         r300->hw.gb_misc.cmd[R300_GB_MISC_SELECT] = 0x00000000;
1557         r300->hw.gb_misc.cmd[R300_GB_MISC_AA_CONFIG] = 0x00000000; /* No antialiasing */
1558
1559         //r300->hw.txe.cmd[R300_TXE_ENABLE] = 0;
1560
1561         r300->hw.unk4200.cmd[1] = r300PackFloat32(0.0);
1562         r300->hw.unk4200.cmd[2] = r300PackFloat32(0.0);
1563         r300->hw.unk4200.cmd[3] = r300PackFloat32(1.0);
1564         r300->hw.unk4200.cmd[4] = r300PackFloat32(1.0);
1565
1566         r300->hw.unk4214.cmd[1] = 0x00050005;
1567
1568         r300->hw.ps.cmd[R300_PS_POINTSIZE] = (6 << R300_POINTSIZE_X_SHIFT) |
1569                                              (6 << R300_POINTSIZE_Y_SHIFT);
1570
1571         r300->hw.unk4230.cmd[1] = 0x01800000;
1572         r300->hw.unk4230.cmd[2] = 0x00020006;
1573         r300->hw.unk4230.cmd[3] = r300PackFloat32(1.0 / 192.0);
1574
1575         r300->hw.unk4260.cmd[1] = 0;
1576         r300->hw.unk4260.cmd[2] = r300PackFloat32(0.0);
1577         r300->hw.unk4260.cmd[3] = r300PackFloat32(1.0);
1578
1579         r300->hw.unk4274.cmd[1] = 0x00000002;
1580         r300->hw.unk4274.cmd[2] = 0x0003AAAA;
1581         r300->hw.unk4274.cmd[3] = 0x00000000;
1582         r300->hw.unk4274.cmd[4] = 0x00000000;
1583
1584         r300->hw.unk4288.cmd[1] = 0x00000000;
1585         r300->hw.unk4288.cmd[2] = 0x00000001;
1586         r300->hw.unk4288.cmd[3] = 0x00000000;
1587         r300->hw.unk4288.cmd[4] = 0x00000000;
1588         r300->hw.unk4288.cmd[5] = 0x00000000;
1589
1590         r300->hw.unk42A0.cmd[1] = 0x00000000;
1591
1592         r300->hw.unk42B4.cmd[1] = 0x00000000;
1593
1594         r300->hw.unk42C0.cmd[1] = 0x4B7FFFFF;
1595         r300->hw.unk42C0.cmd[2] = 0x00000000;
1596
1597
1598         r300->hw.unk43A4.cmd[1] = 0x0000001C;
1599         r300->hw.unk43A4.cmd[2] = 0x2DA49525;
1600
1601         r300->hw.unk43E8.cmd[1] = 0x00FFFFFF;
1602
1603         #if 0
1604         r300->hw.fp.cmd[R300_FP_CNTL0] = 0;
1605         r300->hw.fp.cmd[R300_FP_CNTL1] = 0;
1606         r300->hw.fp.cmd[R300_FP_CNTL2] = 0;
1607         r300->hw.fp.cmd[R300_FP_NODE0] = 0;
1608         r300->hw.fp.cmd[R300_FP_NODE1] = 0;
1609         r300->hw.fp.cmd[R300_FP_NODE2] = 0;
1610         r300->hw.fp.cmd[R300_FP_NODE3] = 0;
1611         #endif
1612
1613         r300->hw.unk46A4.cmd[1] = 0x00001B01;
1614         r300->hw.unk46A4.cmd[2] = 0x00001B0F;
1615         r300->hw.unk46A4.cmd[3] = 0x00001B0F;
1616         r300->hw.unk46A4.cmd[4] = 0x00001B0F;
1617         r300->hw.unk46A4.cmd[5] = 0x00000001;
1618
1619         #if 0
1620         for(i = 1; i <= 64; ++i) {
1621                 /* create NOP instructions */
1622                 r300->hw.fpi[0].cmd[i] = FP_INSTRC(MAD, FP_ARGC(SRC0C_XYZ), FP_ARGC(ONE), FP_ARGC(ZERO));
1623                 r300->hw.fpi[1].cmd[i] = FP_SELC(0,XYZ,NO,FP_TMP(0),0,0);
1624                 r300->hw.fpi[2].cmd[i] = FP_INSTRA(MAD, FP_ARGA(SRC0A), FP_ARGA(ONE), FP_ARGA(ZERO));
1625                 r300->hw.fpi[3].cmd[i] = FP_SELA(0,W,NO,FP_TMP(0),0,0);
1626         }
1627         #endif
1628
1629         r300->hw.unk4BC0.cmd[1] = 0;
1630
1631         r300->hw.unk4BC8.cmd[1] = 0;
1632         r300->hw.unk4BC8.cmd[2] = 0;
1633         r300->hw.unk4BC8.cmd[3] = 0;
1634
1635         #if 0
1636         r300->hw.at.cmd[R300_AT_ALPHA_TEST] = 0;
1637         #endif
1638
1639         r300->hw.at.cmd[R300_AT_UNKNOWN] = 0;
1640         r300->hw.unk4BD8.cmd[1] = 0;
1641
1642         r300->hw.unk4E00.cmd[1] = 0;
1643
1644         #if 0
1645         r300->hw.bld.cmd[R300_BLD_CBLEND] = 0;
1646         r300->hw.bld.cmd[R300_BLD_ABLEND] = 0;
1647         #endif
1648
1649         r300->hw.unk4E10.cmd[1] = 0;
1650         r300->hw.unk4E10.cmd[2] = 0;
1651         r300->hw.unk4E10.cmd[3] = 0;
1652
1653         r300->hw.cb.cmd[R300_CB_OFFSET] =
1654                 r300->radeon.radeonScreen->backOffset +
1655                 r300->radeon.radeonScreen->fbLocation;
1656         r300->hw.cb.cmd[R300_CB_PITCH] = r300->radeon.radeonScreen->backPitch
1657                 | R300_COLOR_UNKNOWN_22_23;
1658
1659         r300->hw.unk4E50.cmd[1] = 0;
1660         r300->hw.unk4E50.cmd[2] = 0;
1661         r300->hw.unk4E50.cmd[3] = 0;
1662         r300->hw.unk4E50.cmd[4] = 0;
1663         r300->hw.unk4E50.cmd[5] = 0;
1664         r300->hw.unk4E50.cmd[6] = 0;
1665         r300->hw.unk4E50.cmd[7] = 0;
1666         r300->hw.unk4E50.cmd[8] = 0;
1667         r300->hw.unk4E50.cmd[9] = 0;
1668
1669         r300->hw.unk4E88.cmd[1] = 0;
1670
1671         r300->hw.unk4EA0.cmd[1] = 0x00000000;
1672         r300->hw.unk4EA0.cmd[2] = 0xffffffff;
1673
1674         r300->hw.unk4F10.cmd[1] = 0x00000002; // depthbuffer format?
1675         r300->hw.unk4F10.cmd[2] = 0x00000000;
1676         r300->hw.unk4F10.cmd[3] = 0x00000003;
1677         r300->hw.unk4F10.cmd[4] = 0x00000000;
1678
1679         /* experiment a bit */
1680         r300->hw.unk4F10.cmd[2] = 0x00000001; // depthbuffer format?
1681
1682         r300->hw.zb.cmd[R300_ZB_OFFSET] =
1683                 r300->radeon.radeonScreen->depthOffset +
1684                 r300->radeon.radeonScreen->fbLocation;
1685         r300->hw.zb.cmd[R300_ZB_PITCH] = r300->radeon.radeonScreen->depthPitch;
1686
1687         r300->hw.unk4F28.cmd[1] = 0;
1688
1689         r300->hw.unk4F30.cmd[1] = 0;
1690         r300->hw.unk4F30.cmd[2] = 0;
1691
1692         r300->hw.unk4F44.cmd[1] = 0;
1693
1694         r300->hw.unk4F54.cmd[1] = 0;
1695
1696         #if 0
1697         ((drm_r300_cmd_header_t*)r300->hw.vpi.cmd)->vpu.count = 0;
1698         for(i = 1; i < R300_VPI_CMDSIZE; i += 4) {
1699                 /* MOV t0, t0 */
1700                 r300->hw.vpi.cmd[i+0] = VP_OUT(ADD,TMP,0,XYZW);
1701                 r300->hw.vpi.cmd[i+1] = VP_IN(TMP,0);
1702                 r300->hw.vpi.cmd[i+2] = VP_ZERO();
1703                 r300->hw.vpi.cmd[i+3] = VP_ZERO();
1704         }
1705
1706         ((drm_r300_cmd_header_t*)r300->hw.vpp.cmd)->vpu.count = 0;
1707         for(i = 1; i < R300_VPP_CMDSIZE; ++i)
1708                 r300->hw.vpp.cmd[i] = 0;
1709         #endif
1710
1711         r300->hw.vps.cmd[R300_VPS_ZERO_0] = 0;
1712         r300->hw.vps.cmd[R300_VPS_ZERO_1] = 0;
1713         r300->hw.vps.cmd[R300_VPS_POINTSIZE] = r300PackFloat32(1.0);
1714         r300->hw.vps.cmd[R300_VPS_ZERO_3] = 0;
1715
1716 //END: TODO
1717
1718         r300->hw.all_dirty = GL_TRUE;
1719 }
1720
1721
1722
1723 /**
1724  * Calculate initial hardware state and register state functions.
1725  * Assumes that the command buffer and state atoms have been
1726  * initialized already.
1727  */
1728 void r300InitState(r300ContextPtr r300)
1729 {
1730         GLcontext *ctx = r300->radeon.glCtx;
1731         GLuint depth_fmt;
1732
1733         radeonInitState(&r300->radeon);
1734
1735         switch (ctx->Visual.depthBits) {
1736         case 16:
1737                 r300->state.depth.scale = 1.0 / (GLfloat) 0xffff;
1738                 depth_fmt = R200_DEPTH_FORMAT_16BIT_INT_Z;
1739                 //r300->state.stencil.clear = 0x00000000;
1740                 break;
1741         case 24:
1742                 r300->state.depth.scale = 1.0 / (GLfloat) 0xffffff;
1743                 depth_fmt = R200_DEPTH_FORMAT_24BIT_INT_Z;
1744                 //r300->state.stencil.clear = 0xff000000;
1745                 break;
1746         default:
1747                 fprintf(stderr, "Error: Unsupported depth %d... exiting\n",
1748                         ctx->Visual.depthBits);
1749                 exit(-1);
1750         }
1751
1752         /* Only have hw stencil when depth buffer is 24 bits deep */
1753         r300->state.hw_stencil = (ctx->Visual.stencilBits > 0 &&
1754                                          ctx->Visual.depthBits == 24);
1755
1756         memset(&(r300->state.texture), 0, sizeof(r300->state.texture));
1757
1758         r300ResetHwState(r300);
1759 }
1760
1761
1762
1763 /**
1764  * Initialize driver's state callback functions
1765  */
1766 void r300InitStateFuncs(struct dd_function_table* functions)
1767 {
1768         radeonInitStateFuncs(functions);
1769
1770         functions->UpdateState = r300InvalidateState;
1771         functions->AlphaFunc = r300AlphaFunc;
1772         functions->BlendColor = r300BlendColor;
1773         functions->BlendEquationSeparate = r300BlendEquationSeparate;
1774         functions->BlendFuncSeparate = r300BlendFuncSeparate;
1775         functions->Enable = r300Enable;
1776         functions->ColorMask = r300ColorMask;
1777         functions->DepthFunc = r300DepthFunc;
1778         functions->DepthMask = r300DepthMask;
1779         functions->CullFace = r300CullFace;
1780         functions->FrontFace = r300FrontFace;
1781
1782         /* Stencil related */
1783         functions->ClearStencil = r300ClearStencil;
1784         functions->StencilFunc = r300StencilFunc;
1785         functions->StencilMask = r300StencilMask;
1786         functions->StencilOp = r300StencilOp;
1787
1788         /* Viewport related */
1789         functions->Viewport = r300Viewport;
1790         functions->DepthRange = r300DepthRange;
1791         functions->PointSize = r300PointSize;
1792 }
1793