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