This is what I have done so far to convert the R200 driver to use t_vertex. It is only a conversion for SW TCL, and it's not quite complete. I've managed to clean up all the crashes that I could find, but I've only tested with gears, geartrain, and tunnel. There are some known problems:

- The textures in tunnel are not quite right. They're sort of zig-zaggy.
- The colors of two of the gears in gears are swapped. The red gear is blue and the blue gear is red. The green gear is correct.


I chopped out all of the _r200_render_stage stuff from r200_swtcl.c. It is unused (due to bad interactions with UT2k3), and was only confusing me. When this patch gets committed, that code can go back in, I think.

There are two hacks that I had to do to get things working. Neither of these needed to be done by the i830 or savage drivers. First, I had to add a "viewport" matrix that remains an identity matrix. This is because the Radeon chips do the viewport transform in hardware. tnl_dd/t_dd_vbtmp.h had the ability to handle hardware like this, but t_vertex apparently does not. Second, I had to force TNL to always produce project coordinates. Again, the Radeon hardware can do the final projection in hardware almost all the time, but due to the way the i830 and savage drivers use use tnl->vb.NdcPtr (actually VB->NdcPtr) I couldn't see a way around this. I may just be missing something there.

I do have one other question that probably only Keith or Daniel can answer. :) Can t_vertex replace the immediate-mode API code-gen in the radeon and r200 drivers? It seems like it should be able to, but I'm not sure I can see exactly how. Does the HW TCL side just need a tnl_attr_map just like the SW TCL side? I think looking at the SW TCL code for so long has fried my brain...

In any case, I won't have a chance to look at this again in until probably next Wednesday. If someone could pick this up and finish it off, that would be cool. I think it's more important to get it done soon than have my name in the commit log. :)

? src/glut/glx/depend
? src/glw/depend
? src/mesa/depend
? src/mesa/x86/gen_matypes
? src/mesa/x86/matypes.h
Index: src/mesa/drivers/dri/r200/r200_context.c
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/drivers/dri/r200/r200_context.c,v
retrieving revision 1.22
diff -u -d -r1.22 r200_context.c
--- a/src/mesa/drivers/dri/r200/r200_context.c  11 Mar 2004 20:35:40 -0000      1.22
+++ b/src/mesa/drivers/dri/r200/r200_context.c  17 Apr 2004 04:49:55 -0000
@@ -391,6 +391,7 @@
    _tnl_allow_vertex_fog( ctx, GL_TRUE );
 
 
+   _math_matrix_ctr( &rmesa->swtcl.ViewportMatrix );
    _math_matrix_ctr( &rmesa->TexGenMatrix[0] );
    _math_matrix_ctr( &rmesa->TexGenMatrix[1] );
    _math_matrix_ctr( &rmesa->tmpmat );
Index: src/mesa/drivers/dri/r200/r200_context.h
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/drivers/dri/r200/r200_context.h,v
retrieving revision 1.12
diff -u -d -r1.12 r200_context.h
--- a/src/mesa/drivers/dri/r200/r200_context.h  11 Mar 2004 20:35:40 -0000      1.12
+++ b/src/mesa/drivers/dri/r200/r200_context.h  17 Apr 2004 04:49:55 -0000
@@ -39,6 +39,7 @@
 #ifdef GLX_DIRECT_RENDERING
 
 #include <inttypes.h>
+#include "tnl/t_vertex.h"
 #include "drm.h"
 #include "radeon_drm.h"
 #include "dri_util.h"
@@ -611,12 +612,13 @@
 /* r200_swtcl.c
  */
 struct r200_swtcl_info {
-   GLuint SetupIndex;
-   GLuint SetupNewInputs;
    GLuint RenderIndex;
    GLuint vertex_size;
-   GLuint vertex_stride_shift;
-   GLuint vertex_format;
+
+   struct tnl_attr_map vertex_attrs[VERT_ATTRIB_MAX];
+   GLuint vertex_attr_count;
+   GLmatrix ViewportMatrix;
+
    GLubyte *verts;
 
    /* Fallback rasterization functions
Index: src/mesa/drivers/dri/r200/r200_swtcl.c
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/drivers/dri/r200/r200_swtcl.c,v
retrieving revision 1.9
diff -u -d -r1.9 r200_swtcl.c
--- a/src/mesa/drivers/dri/r200/r200_swtcl.c    20 Jan 2004 02:49:27 -0000      1.9
+++ b/src/mesa/drivers/dri/r200/r200_swtcl.c    17 Apr 2004 04:49:55 -0000
@@ -56,239 +56,134 @@
 #include "r200_swtcl.h"
 #include "r200_tcl.h"
 
-/***********************************************************************
- *              Build render functions from dd templates               *
- ***********************************************************************/
-
-
-#define R200_XYZW_BIT          0x01
-#define R200_RGBA_BIT          0x02
-#define R200_SPEC_BIT          0x04
-#define R200_TEX0_BIT          0x08
-#define R200_TEX1_BIT          0x10
-#define R200_PTEX_BIT          0x20
-#define R200_MAX_SETUP 0x40
 
 static void flush_last_swtcl_prim( r200ContextPtr rmesa  );
 
-static struct {
-   void                (*emit)( GLcontext *, GLuint, GLuint, void *, GLuint );
-   interp_func         interp;
-   copy_pv_func                copy_pv;
-   GLboolean           (*check_tex_sizes)( GLcontext *ctx );
-   GLuint               vertex_size;
-   GLuint               vertex_format;
-} setup_tab[R200_MAX_SETUP];
-
-
-static int se_vtx_fmt_0[] = {
-   0,
-
-   (R200_VTX_XY |
-    R200_VTX_Z0 |
-    (R200_VTX_PK_RGBA << R200_VTX_COLOR_0_SHIFT)),
-
-   (R200_VTX_XY |
-    R200_VTX_Z0 |
-    R200_VTX_W0 |
-    (R200_VTX_PK_RGBA << R200_VTX_COLOR_0_SHIFT) |
-    (R200_VTX_PK_RGBA << R200_VTX_COLOR_1_SHIFT)),
-
-   (R200_VTX_XY |
-    R200_VTX_Z0 |
-    R200_VTX_W0 |
-    (R200_VTX_PK_RGBA << R200_VTX_COLOR_0_SHIFT) |
-    (R200_VTX_PK_RGBA << R200_VTX_COLOR_1_SHIFT)),
-
-   (R200_VTX_XY |
-    R200_VTX_Z0 |
-    R200_VTX_W0 |
-    (R200_VTX_PK_RGBA << R200_VTX_COLOR_0_SHIFT) |
-    (R200_VTX_PK_RGBA << R200_VTX_COLOR_1_SHIFT)),
-
-   (R200_VTX_XY |
-    R200_VTX_Z0 |
-    R200_VTX_W0 |
-    (R200_VTX_PK_RGBA << R200_VTX_COLOR_0_SHIFT) |
-    (R200_VTX_PK_RGBA << R200_VTX_COLOR_1_SHIFT))
-};
-
-static int se_vtx_fmt_1[] = {
-   0,
-   0,
-   0,
-   ((2 << R200_VTX_TEX0_COMP_CNT_SHIFT)),
-   ((2 << R200_VTX_TEX0_COMP_CNT_SHIFT) |
-    (2 << R200_VTX_TEX1_COMP_CNT_SHIFT)),
-   ((3 << R200_VTX_TEX0_COMP_CNT_SHIFT) |
-    (3 << R200_VTX_TEX1_COMP_CNT_SHIFT)),
-};
-
-#define TINY_VERTEX_FORMAT     1
-#define NOTEX_VERTEX_FORMAT    2
-#define TEX0_VERTEX_FORMAT     3
-#define TEX1_VERTEX_FORMAT     4
-#define PROJ_TEX1_VERTEX_FORMAT        5
-#define TEX2_VERTEX_FORMAT 0
-#define TEX3_VERTEX_FORMAT 0
-#define PROJ_TEX3_VERTEX_FORMAT 0
-
-#define DO_XYZW (IND & R200_XYZW_BIT)
-#define DO_RGBA (IND & R200_RGBA_BIT)
-#define DO_SPEC (IND & R200_SPEC_BIT)
-#define DO_FOG  (IND & R200_SPEC_BIT)
-#define DO_TEX0 (IND & R200_TEX0_BIT)
-#define DO_TEX1 (IND & R200_TEX1_BIT)
-#define DO_TEX2 0
-#define DO_TEX3 0
-#define DO_PTEX (IND & R200_PTEX_BIT)
-
-#define VERTEX r200Vertex
-#define VERTEX_COLOR r200_color_t
-#define GET_VIEWPORT_MAT() 0
-#define GET_TEXSOURCE(n)  n
-#define GET_VERTEX_FORMAT() R200_CONTEXT(ctx)->swtcl.vertex_format
-#define GET_VERTEX_STORE() R200_CONTEXT(ctx)->swtcl.verts
-#define GET_VERTEX_SIZE() R200_CONTEXT(ctx)->swtcl.vertex_size * sizeof(GLuint)
-
-#define HAVE_HW_VIEWPORT    1
-#define HAVE_HW_DIVIDE      (IND & ~(R200_XYZW_BIT|R200_RGBA_BIT))
-#define HAVE_TINY_VERTICES  1
-#define HAVE_RGBA_COLOR     1
-#define HAVE_NOTEX_VERTICES 1
-#define HAVE_TEX0_VERTICES  1
-#define HAVE_TEX1_VERTICES  1
-#define HAVE_TEX2_VERTICES  0
-#define HAVE_TEX3_VERTICES  0
-#define HAVE_PTEX_VERTICES  1
-
-#define CHECK_HW_DIVIDE    (!(ctx->_TriangleCaps & (DD_TRI_LIGHT_TWOSIDE| \
-                                                    DD_TRI_UNFILLED)))
-
-#define INTERP_VERTEX setup_tab[R200_CONTEXT(ctx)->swtcl.SetupIndex].interp
-#define COPY_PV_VERTEX setup_tab[R200_CONTEXT(ctx)->swtcl.SetupIndex].copy_pv
-
-
-/***********************************************************************
- *         Generate  pv-copying and translation functions              *
- ***********************************************************************/
-
-#define TAG(x) r200_##x
-#define IND ~0
-#include "tnl_dd/t_dd_vb.c"
-#undef IND
-
 
 /***********************************************************************
- *             Generate vertex emit and interp functions               *
+ *                         Initialization 
  ***********************************************************************/
 
-#define IND (R200_XYZW_BIT|R200_RGBA_BIT)
-#define TAG(x) x##_wg
-#include "tnl_dd/t_dd_vbtmp.h"
-
-#define IND (R200_XYZW_BIT|R200_RGBA_BIT|R200_TEX0_BIT)
-#define TAG(x) x##_wgt0
-#include "tnl_dd/t_dd_vbtmp.h"
-
-#define IND (R200_XYZW_BIT|R200_RGBA_BIT|R200_TEX0_BIT|R200_PTEX_BIT)
-#define TAG(x) x##_wgpt0
-#include "tnl_dd/t_dd_vbtmp.h"
-
-#define IND (R200_XYZW_BIT|R200_RGBA_BIT|R200_TEX0_BIT|R200_TEX1_BIT)
-#define TAG(x) x##_wgt0t1
-#include "tnl_dd/t_dd_vbtmp.h"
-
-#define IND (R200_XYZW_BIT|R200_RGBA_BIT|R200_TEX0_BIT|R200_TEX1_BIT|\
-             R200_PTEX_BIT)
-#define TAG(x) x##_wgpt0t1
-#include "tnl_dd/t_dd_vbtmp.h"
+#define EMIT_SZ(sz)   (EMIT_1F + (sz) - 1)
+#define EMIT_ATTR( ATTR, STYLE, F0 )                                   \
+do {                                                                   \
+   rmesa->swtcl.vertex_attrs[rmesa->swtcl.vertex_attr_count].attrib = (ATTR);  \
+   rmesa->swtcl.vertex_attrs[rmesa->swtcl.vertex_attr_count].format = (STYLE); \
+   rmesa->swtcl.vertex_attr_count++;                                   \
+   fmt_0 |= F0;                                                                \
+} while (0)
 
-#define IND (R200_XYZW_BIT|R200_RGBA_BIT|R200_SPEC_BIT)
-#define TAG(x) x##_wgfs
-#include "tnl_dd/t_dd_vbtmp.h"
+#define EMIT_PAD( N )                                                  \
+do {                                                                   \
+   rmesa->swtcl.vertex_attrs[rmesa->swtcl.vertex_attr_count].attrib = 0;              
 \
+   rmesa->swtcl.vertex_attrs[rmesa->swtcl.vertex_attr_count].format = EMIT_PAD;       
 \
+   rmesa->swtcl.vertex_attrs[rmesa->swtcl.vertex_attr_count].offset = (N);            
 \
+   rmesa->swtcl.vertex_attr_count++;                                   \
+} while (0)
 
-#define IND (R200_XYZW_BIT|R200_RGBA_BIT|R200_SPEC_BIT|\
-            R200_TEX0_BIT)
-#define TAG(x) x##_wgfst0
-#include "tnl_dd/t_dd_vbtmp.h"
+static void r200SetVertexFormat( GLcontext *ctx )
+{
+   r200ContextPtr rmesa = R200_CONTEXT( ctx );
+   TNLcontext *tnl = TNL_CONTEXT(ctx);
+   struct vertex_buffer *VB = &tnl->vb;
+   GLuint index = tnl->render_inputs;
+   int fmt_0;
+   int fmt_1;
+   GLboolean is_tiny = GL_TRUE;
 
-#define IND (R200_XYZW_BIT|R200_RGBA_BIT|R200_SPEC_BIT|\
-            R200_TEX0_BIT|R200_PTEX_BIT)
-#define TAG(x) x##_wgfspt0
-#include "tnl_dd/t_dd_vbtmp.h"
 
-#define IND (R200_XYZW_BIT|R200_RGBA_BIT|R200_SPEC_BIT|\
-            R200_TEX0_BIT|R200_TEX1_BIT)
-#define TAG(x) x##_wgfst0t1
-#include "tnl_dd/t_dd_vbtmp.h"
+   /* Important:
+    */
+   VB->AttribPtr[VERT_ATTRIB_POS] = VB->NdcPtr;
+   assert( VB->NdcPtr != NULL );
+   rmesa->swtcl.vertex_attr_count = 0;
 
-#define IND (R200_XYZW_BIT|R200_RGBA_BIT|R200_SPEC_BIT|\
-            R200_TEX0_BIT|R200_TEX1_BIT|R200_PTEX_BIT)
-#define TAG(x) x##_wgfspt0t1
-#include "tnl_dd/t_dd_vbtmp.h"
+   fmt_0 = R200_VTX_XY | R200_VTX_Z0;
+   fmt_1 = 0;
 
+   /* EMIT_ATTR's must be in order as they tell t_vertex.c how to
+    * build up a hardware vertex.
+    */
+   if (index & (_TNL_BITS_TEX_ANY | _TNL_BIT_COLOR1 | _TNL_BIT_FOG)) {
+      EMIT_ATTR( _TNL_ATTRIB_POS, EMIT_4F_VIEWPORT, R200_VTX_W0 );
+      is_tiny = GL_FALSE;
+   }
+   else {
+      EMIT_ATTR( _TNL_ATTRIB_POS, EMIT_3F_VIEWPORT, 0 );
+   }
 
-/***********************************************************************
- *                         Initialization 
- ***********************************************************************/
+   EMIT_ATTR( _TNL_ATTRIB_COLOR0, EMIT_4UB_4F_RGBA, (R200_VTX_PK_RGBA << 
R200_VTX_COLOR_0_SHIFT) );
 
-static void init_setup_tab( void )
-{
-   init_wg();
-   init_wgt0();
-   init_wgpt0();
-   init_wgt0t1();
-   init_wgpt0t1();
-   init_wgfs();
-   init_wgfst0();
-   init_wgfspt0();
-   init_wgfst0t1();
-   init_wgfspt0t1();
-}
+   if (index & (_TNL_BIT_COLOR1|_TNL_BIT_FOG)) {
+      is_tiny = GL_FALSE;
 
+      if (index & _TNL_BIT_COLOR1) {
+        EMIT_ATTR( _TNL_ATTRIB_COLOR1, EMIT_3UB_3F_RGB, (R200_VTX_PK_RGBA << 
R200_VTX_COLOR_1_SHIFT) );
+      }
+      else {
+        EMIT_PAD( 3 );
+      }
 
+      if (index & _TNL_BIT_FOG) {
+        EMIT_ATTR( _TNL_ATTRIB_FOG, EMIT_1UB_1F, (R200_VTX_PK_RGBA << 
R200_VTX_COLOR_1_SHIFT) );
+      }
+      else {
+        EMIT_PAD( 1 );
+      }
+   }
 
-void r200PrintSetupFlags(char *msg, GLuint flags )
-{
-   fprintf(stderr, "%s(%x): %s%s%s%s%s%s\n",
-          msg,
-          (int)flags,
-          (flags & R200_XYZW_BIT)      ? " xyzw," : "",
-          (flags & R200_RGBA_BIT)     ? " rgba," : "",
-          (flags & R200_SPEC_BIT)     ? " spec/fog," : "",
-          (flags & R200_TEX0_BIT)     ? " tex-0," : "",
-          (flags & R200_TEX1_BIT)     ? " tex-1," : "",
-          (flags & R200_PTEX_BIT)     ? " proj-tex," : "");
-}
+   if (index & _TNL_BITS_TEX_ANY) {
+      int i, last_stage = 0;
 
+      /* Still using 2 as max tex units, but this code is fine for all
+       * 8 units supported by mesa:
+       */
+      for (i = 0; i < 2 ; i++) 
+        if (index & _TNL_BIT_TEX(i))
+           last_stage = i+1;
+        
 
+      for (i = 0; i < last_stage; i++) {
+        GLuint sz = VB->TexCoordPtr[i]->size;
+        GLuint emit;
 
-static void r200SetVertexFormat( GLcontext *ctx, GLuint ind ) 
-{
-   r200ContextPtr rmesa = R200_CONTEXT( ctx );
-   TNLcontext *tnl = TNL_CONTEXT(ctx);
+        /* r200 doesn't like 1D or 4D texcoords (is that true?):
+         */
+        switch (sz) {
+        case 1: 
+        case 2: 
+        case 3:                /* no attempt at cube texturing so far */
+           emit = EMIT_2F; 
+           sz = 2; 
+           break;
+        case 4: 
+           emit = EMIT_3F_XYW; 
+           sz = 3;     
+           break;
+        default: 
+           continue;
+        };
+       
+        fmt_1 |= sz << (3 * i);
+        EMIT_ATTR( _TNL_ATTRIB_TEX0+i, EMIT_SZ(sz), 0 );
+      }
+   }
 
-   rmesa->swtcl.SetupIndex = ind;
 
-   if (ctx->_TriangleCaps & (DD_TRI_LIGHT_TWOSIDE|DD_TRI_UNFILLED)) {
-      tnl->Driver.Render.Interp = r200_interp_extras;
-      tnl->Driver.Render.CopyPV = r200_copy_pv_extras;
-   }
-   else {
-      tnl->Driver.Render.Interp = setup_tab[ind].interp;
-      tnl->Driver.Render.CopyPV = setup_tab[ind].copy_pv;
-   }
 
-   if (setup_tab[ind].vertex_format != rmesa->swtcl.vertex_format) {
-      int i;
+   if ( (rmesa->hw.vtx.cmd[VTX_VTXFMT_0] != fmt_0)
+       || (rmesa->hw.vtx.cmd[VTX_VTXFMT_1] != fmt_1) ) {
       R200_NEWPRIM(rmesa);
-      i = rmesa->swtcl.vertex_format = setup_tab[ind].vertex_format;
-      rmesa->swtcl.vertex_size = setup_tab[ind].vertex_size;
-
       R200_STATECHANGE( rmesa, vtx );
-      rmesa->hw.vtx.cmd[VTX_VTXFMT_0] = se_vtx_fmt_0[i];
-      rmesa->hw.vtx.cmd[VTX_VTXFMT_1] = se_vtx_fmt_1[i];
+      rmesa->hw.vtx.cmd[VTX_VTXFMT_0] = fmt_0;
+      rmesa->hw.vtx.cmd[VTX_VTXFMT_1] = fmt_1;
+
+      rmesa->swtcl.vertex_size =
+         _tnl_install_attrs( ctx,
+                             rmesa->swtcl.vertex_attrs, 
+                             rmesa->swtcl.vertex_attr_count,
+                             rmesa->swtcl.ViewportMatrix.m, 0 );
+      rmesa->swtcl.vertex_size /= 4;
    }
 
    {
@@ -299,7 +194,7 @@
       /* HW perspective divide is a win, but tiny vertex formats are a
        * bigger one.
        */
-      if (setup_tab[ind].vertex_format == TINY_VERTEX_FORMAT ||
+      if (1 || is_tiny ||
          (ctx->_TriangleCaps & (DD_TRI_LIGHT_TWOSIDE|DD_TRI_UNFILLED))) {
         needproj = GL_TRUE;
         vte |= R200_VTX_XY_FMT | R200_VTX_Z_FMT;
@@ -329,50 +224,30 @@
 {
    r200ContextPtr rmesa = R200_CONTEXT( ctx );
 
-   if (!setup_tab[rmesa->swtcl.SetupIndex].check_tex_sizes(ctx)) {
-      r200SetVertexFormat( ctx, rmesa->swtcl.SetupIndex | R200_PTEX_BIT);
-   }
-   
+   r200SetVertexFormat( ctx );
+
    if (rmesa->dma.flush != 0 && 
        rmesa->dma.flush != flush_last_swtcl_prim)
       rmesa->dma.flush( rmesa );
 }
 
 
-void r200BuildVertices( GLcontext *ctx, GLuint start, GLuint count,
-                          GLuint newinputs )
-{
-   r200ContextPtr rmesa = R200_CONTEXT( ctx );
-   GLuint stride = rmesa->swtcl.vertex_size * sizeof(int);
-   GLubyte *v = ((GLubyte *)rmesa->swtcl.verts + (start * stride));
-
-   newinputs |= rmesa->swtcl.SetupNewInputs;
-   rmesa->swtcl.SetupNewInputs = 0;
-
-   if (!newinputs)
-      return;
-
-   setup_tab[rmesa->swtcl.SetupIndex].emit( ctx, start, count, v, stride );
-}
-
-
 void r200ChooseVertexState( GLcontext *ctx )
 {
    r200ContextPtr rmesa = R200_CONTEXT( ctx );
-   GLuint ind = (R200_XYZW_BIT | R200_RGBA_BIT);
-
-   if (!rmesa->TclFallback || rmesa->Fallback)
-      return;
+   TNLcontext *tnl = TNL_CONTEXT(ctx);
+   struct vertex_buffer *VB = &tnl->vb;
 
-   if (ctx->Fog.Enabled || (ctx->_TriangleCaps & DD_SEPARATE_SPECULAR))
-      ind |= R200_SPEC_BIT;
+   _tnl_need_projected_coords( ctx, GL_TRUE );
 
-   if (ctx->Texture._EnabledUnits & 0x2)  /* unit 1 enabled */
-      ind |= R200_TEX0_BIT|R200_TEX1_BIT;
-   else if (ctx->Texture._EnabledUnits & 0x1)  /* unit 1 enabled */
-      ind |= R200_TEX0_BIT;
+   rmesa->swtcl.vertex_attr_count = 0;
 
-   r200SetVertexFormat( ctx, ind );
+   _tnl_invalidate_vertex_state( ctx, ~0 );
+   _tnl_invalidate_vertices( ctx, ~0 );
+   _tnl_install_attrs( ctx,
+                      rmesa->swtcl.vertex_attrs, 
+                      rmesa->swtcl.vertex_attr_count,
+                      rmesa->swtcl.ViewportMatrix.m, 0 ); 
 }
 
 
@@ -445,251 +320,6 @@
 }
 
 
-
-
-static void *r200_emit_contiguous_verts( GLcontext *ctx, 
-                                        GLuint start, 
-                                        GLuint count,
-                                        void *dest)
-{
-   r200ContextPtr rmesa = R200_CONTEXT(ctx);
-   GLuint stride = rmesa->swtcl.vertex_size * 4;
-   setup_tab[rmesa->swtcl.SetupIndex].emit( ctx, start, count, dest, stride );
-   return (void *)((char *)dest + stride * (count - start));
-}
-
-
-
-void r200_emit_indexed_verts( GLcontext *ctx, GLuint start, GLuint count )
-{
-   r200ContextPtr rmesa = R200_CONTEXT(ctx);
-
-   r200AllocDmaRegionVerts( rmesa, 
-                             &rmesa->swtcl.indexed_verts, 
-                             count - start,
-                             rmesa->swtcl.vertex_size * 4, 
-                             64);
-
-   setup_tab[rmesa->swtcl.SetupIndex].emit( 
-      ctx, start, count, 
-      rmesa->swtcl.indexed_verts.address + rmesa->swtcl.indexed_verts.start, 
-      rmesa->swtcl.vertex_size * 4 );
-}
-
-
-/*
- * Render unclipped vertex buffers by emitting vertices directly to
- * dma buffers.  Use strip/fan hardware primitives where possible.
- * Try to simulate missing primitives with indexed vertices.
- */
-#define HAVE_POINTS      1
-#define HAVE_LINES       1
-#define HAVE_LINE_STRIPS 1
-#define HAVE_TRIANGLES   1
-#define HAVE_TRI_STRIPS  1
-#define HAVE_TRI_STRIP_1 0
-#define HAVE_TRI_FANS    1
-#define HAVE_QUADS       1
-#define HAVE_QUAD_STRIPS 1
-#define HAVE_POLYGONS    1
-#define HAVE_ELTS        1
-
-static const GLuint hw_prim[GL_POLYGON+1] = {
-   R200_VF_PRIM_POINTS,
-   R200_VF_PRIM_LINES,
-   0,
-   R200_VF_PRIM_LINE_STRIP,
-   R200_VF_PRIM_TRIANGLES,
-   R200_VF_PRIM_TRIANGLE_STRIP,
-   R200_VF_PRIM_TRIANGLE_FAN,
-   R200_VF_PRIM_QUADS,
-   R200_VF_PRIM_QUAD_STRIP,
-   R200_VF_PRIM_POLYGON
-};
-
-static __inline void r200DmaPrimitive( r200ContextPtr rmesa, GLenum prim )
-{
-   R200_NEWPRIM( rmesa );
-   rmesa->swtcl.hw_primitive = hw_prim[prim];
-   assert(rmesa->dma.current.ptr == rmesa->dma.current.start);
-}
-
-static __inline void r200EltPrimitive( r200ContextPtr rmesa, GLenum prim )
-{
-   R200_NEWPRIM( rmesa );
-   rmesa->swtcl.hw_primitive = hw_prim[prim] | R200_VF_PRIM_WALK_IND;
-}
-
-
-
-
-#define LOCAL_VARS r200ContextPtr rmesa = R200_CONTEXT(ctx)
-#define ELTS_VARS(buf)  GLushort *dest = buf
-#define INIT( prim ) r200DmaPrimitive( rmesa, prim )
-#define ELT_INIT(prim) r200EltPrimitive( rmesa, prim )
-#define FLUSH()  R200_NEWPRIM( rmesa )
-#define GET_CURRENT_VB_MAX_VERTS() \
-  (((int)rmesa->dma.current.end - (int)rmesa->dma.current.ptr) / 
(rmesa->swtcl.vertex_size*4))
-#define GET_SUBSEQUENT_VB_MAX_VERTS() \
-  ((RADEON_BUFFER_SIZE) / (rmesa->swtcl.vertex_size*4))
-
-#define GET_CURRENT_VB_MAX_ELTS() \
-  ((R200_CMD_BUF_SZ - (rmesa->store.cmd_used + 16)) / 2)
-#define GET_SUBSEQUENT_VB_MAX_ELTS() \
-  ((R200_CMD_BUF_SZ - 1024) / 2)
-
-static void *r200_alloc_elts( r200ContextPtr rmesa, int nr )
-{
-   if (rmesa->dma.flush == r200FlushElts &&
-       rmesa->store.cmd_used + nr*2 < R200_CMD_BUF_SZ) {
-
-      rmesa->store.cmd_used += nr*2;
-
-      return (void *)(rmesa->store.cmd_buf + rmesa->store.cmd_used);
-   }
-   else {
-      if (rmesa->dma.flush) {
-        rmesa->dma.flush( rmesa );
-      }
-
-      r200EmitVertexAOS( rmesa,
-                          rmesa->swtcl.vertex_size,
-                          (rmesa->r200Screen->gart_buffer_offset +
-                           rmesa->swtcl.indexed_verts.buf->buf->idx *
-                           RADEON_BUFFER_SIZE +
-                           rmesa->swtcl.indexed_verts.start));
-
-      return (void *) r200AllocEltsOpenEnded( rmesa,
-                                             rmesa->swtcl.hw_primitive,
-                                             nr );
-   }
-}
-
-#define ALLOC_ELTS(nr) r200_alloc_elts(rmesa, nr)
-
-
-
-#ifdef MESA_BIG_ENDIAN
-/* We could do without (most of) this ugliness if dest was always 32 bit word 
aligned... */
-#define EMIT_ELT(offset, x) do {                                \
-        int off = offset + ( ( (GLuint)dest & 0x2 ) >> 1 );     \
-        GLushort *des = (GLushort *)( (GLuint)dest & ~0x2 );    \
-        (des)[ off + 1 - 2 * ( off & 1 ) ] = (GLushort)(x); } while (0)
-#else
-#define EMIT_ELT(offset, x) (dest)[offset] = (GLushort) (x)
-#endif
-#define EMIT_TWO_ELTS(offset, x, y)  *(GLuint *)(dest+offset) = ((y)<<16)|(x);
-#define INCR_ELTS( nr ) dest += nr
-#define ELTPTR dest
-#define RELEASE_ELT_VERTS() \
-  r200ReleaseDmaRegion( rmesa, &rmesa->swtcl.indexed_verts, __FUNCTION__ )
-
-#define EMIT_INDEXED_VERTS( ctx, start, count ) \
-  r200_emit_indexed_verts( ctx, start, count )
-
-
-#define ALLOC_VERTS( nr ) \
-  r200AllocDmaLowVerts( rmesa, nr, rmesa->swtcl.vertex_size * 4 )
-#define EMIT_VERTS( ctx, j, nr, buf ) \
-  r200_emit_contiguous_verts(ctx, j, (j)+(nr), buf)
-
-
-
-#define TAG(x) r200_dma_##x
-#include "tnl_dd/t_dd_dmatmp.h"
-
-
-/**********************************************************************/
-/*                          Render pipeline stage                     */
-/**********************************************************************/
-
-
-
-static GLboolean r200_run_render( GLcontext *ctx,
-                                   struct tnl_pipeline_stage *stage )
-{
-   r200ContextPtr rmesa = R200_CONTEXT(ctx);
-   TNLcontext *tnl = TNL_CONTEXT(ctx);
-   struct vertex_buffer *VB = &tnl->vb;
-   GLuint i;
-   render_func *tab = TAG(render_tab_verts);
-
-   if (rmesa->swtcl.indexed_verts.buf && (!VB->Elts || stage->changed_inputs)) 
-      RELEASE_ELT_VERTS();
-       
-   
-
-   if ((R200_DEBUG & DEBUG_VERTS) ||
-       rmesa->swtcl.RenderIndex != 0 ||
-       !r200_dma_validate_render( ctx, VB ))
-      return GL_TRUE;          
-
-   if (VB->Elts) {
-      tab = TAG(render_tab_elts);
-      if (!rmesa->swtcl.indexed_verts.buf) {
-        if (VB->Count > GET_SUBSEQUENT_VB_MAX_VERTS())
-           return GL_TRUE;
-        EMIT_INDEXED_VERTS(ctx, 0, VB->Count);
-      }
-   }
-
-   tnl->Driver.Render.Start( ctx );
-
-   for (i = 0 ; i < VB->PrimitiveCount ; i++)
-   {
-      GLuint prim = VB->Primitive[i].mode;
-      GLuint start = VB->Primitive[i].start;
-      GLuint length = VB->Primitive[i].count;
-
-      if (!length)
-        continue;
-
-      if (R200_DEBUG & DEBUG_PRIMS)
-        fprintf(stderr, "r200_render.c: prim %s %d..%d\n", 
-                _mesa_lookup_enum_by_nr(prim & PRIM_MODE_MASK), 
-                start, start+length);
-
-      tab[prim & PRIM_MODE_MASK]( ctx, start, start + length, prim );
-   }
-
-   tnl->Driver.Render.Finish( ctx );
-
-   return GL_FALSE;            /* finished the pipe */
-}
-
-
-
-static void r200_check_render( GLcontext *ctx,
-                                struct tnl_pipeline_stage *stage )
-{
-   stage->inputs = TNL_CONTEXT(ctx)->render_inputs;
-}
-
-
-static void dtr( struct tnl_pipeline_stage *stage )
-{
-   (void)stage;
-}
-
-
-const struct tnl_pipeline_stage _r200_render_stage =
-{
-   "r200 render",
-   (_DD_NEW_SEPARATE_SPECULAR |
-    _NEW_TEXTURE|
-    _NEW_FOG|
-    _NEW_RENDERMODE),          /* re-check (new inputs) */
-   0,                          /* re-run (always runs) */
-   GL_TRUE,                    /* active */
-   0, 0,                       /* inputs (set in check_render), outputs */
-   0, 0,                       /* changed_inputs, private */
-   dtr,                                /* destructor */
-   r200_check_render,          /* check - initially set to alloc data */
-   r200_run_render             /* run */
-};
-
-
-
 /**************************************************************************/
 
 
@@ -710,16 +340,22 @@
 static void r200RenderPrimitive( GLcontext *ctx, GLenum prim );
 static void r200ResetLineStipple( GLcontext *ctx );
 
-#undef HAVE_QUADS
-#define HAVE_QUADS 0
-
-#undef HAVE_QUAD_STRIPS
-#define HAVE_QUAD_STRIPS 0
-
 /***********************************************************************
  *                    Emit primitives as inline vertices               *
  ***********************************************************************/
 
+#define HAVE_POINTS      1
+#define HAVE_LINES       1
+#define HAVE_LINE_STRIPS 1
+#define HAVE_TRIANGLES   1
+#define HAVE_TRI_STRIPS  1
+#define HAVE_TRI_STRIP_1 0
+#define HAVE_TRI_FANS    1
+#define HAVE_QUADS       0
+#define HAVE_QUAD_STRIPS 0
+#define HAVE_POLYGONS    1
+#define HAVE_ELTS        0
+
 #undef LOCAL_VARS
 #undef ALLOC_VERTS
 #define CTX_ARG r200ContextPtr rmesa
@@ -732,7 +368,7 @@
 #define VERT(x) (r200Vertex *)(r200verts + ((x) * vertsize * sizeof(int)))
 #define VERTEX r200Vertex 
 #define DO_DEBUG_VERTS (1 && (R200_DEBUG & DEBUG_VERTS))
-#define PRINT_VERTEX(v) r200_print_vertex(rmesa->glCtx, v)
+
 #undef TAG
 #define TAG(x) r200_##x
 #include "tnl_dd/t_dd_triemit.h"
@@ -1041,11 +677,17 @@
    else {
       rmesa->Fallback &= ~bit;
       if (oldfallback == bit) {
+        struct vertex_buffer *VB = &tnl->vb;
+
         _swrast_flush( ctx );
         tnl->Driver.Render.Start = r200RenderStart;
         tnl->Driver.Render.PrimitiveNotify = r200RenderPrimitive;
         tnl->Driver.Render.Finish = r200RenderFinish;
-        tnl->Driver.Render.BuildVertices = r200BuildVertices;
+
+        tnl->Driver.Render.BuildVertices = _tnl_build_vertices;
+        tnl->Driver.Render.CopyPV = _tnl_copy_pv;
+        tnl->Driver.Render.Interp = _tnl_interp;
+
         tnl->Driver.Render.ResetLineStipple = r200ResetLineStipple;
         TCL_FALLBACK( ctx, R200_TCL_FALLBACK_RASTER, GL_FALSE );
         if (rmesa->TclFallback) {
@@ -1089,7 +731,9 @@
 
    /* Choose tiny vertex format
     */
+#if 0
    r200SetVertexFormat( ctx, R200_XYZW_BIT | R200_RGBA_BIT );
+#endif
 
    /* Ready for point primitives:
     */
@@ -1231,7 +875,6 @@
 
    if (firsttime) {
       init_rast_tab();
-      init_setup_tab();
       firsttime = 0;
    }
 
@@ -1239,9 +882,14 @@
    tnl->Driver.Render.Finish = r200RenderFinish;
    tnl->Driver.Render.PrimitiveNotify = r200RenderPrimitive;
    tnl->Driver.Render.ResetLineStipple = r200ResetLineStipple;
-   tnl->Driver.Render.BuildVertices = r200BuildVertices;
+   tnl->Driver.Render.BuildVertices = _tnl_build_vertices;
+   tnl->Driver.Render.CopyPV = _tnl_copy_pv;
+   tnl->Driver.Render.Interp = _tnl_interp;
 
-   rmesa->swtcl.verts = (GLubyte *)ALIGN_MALLOC( size * 16 * 4, 32 );
+   _tnl_init_vertices( ctx, ctx->Const.MaxArrayLockSize + 12, 
+                      22 * sizeof(GLfloat) );
+   
+   rmesa->swtcl.verts = (GLubyte *)tnl->clipspace.vertex_buf;
    rmesa->swtcl.RenderIndex = ~0;
    rmesa->swtcl.render_primitive = GL_TRIANGLES;
    rmesa->swtcl.hw_primitive = 0;
@@ -1254,9 +902,4 @@
 
    if (rmesa->swtcl.indexed_verts.buf) 
       r200ReleaseDmaRegion( rmesa, &rmesa->swtcl.indexed_verts, __FUNCTION__ );
-
-   if (rmesa->swtcl.verts) {
-      ALIGN_FREE(rmesa->swtcl.verts);
-      rmesa->swtcl.verts = 0;
-   }
 }
Index: src/mesa/drivers/dri/r200/r200_tcl.c
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/drivers/dri/r200/r200_tcl.c,v
retrieving revision 1.6
diff -u -d -r1.6 r200_tcl.c
--- a/src/mesa/drivers/dri/r200/r200_tcl.c      9 Dec 2003 14:18:41 -0000       1.6
+++ b/src/mesa/drivers/dri/r200/r200_tcl.c      17 Apr 2004 04:49:55 -0000
@@ -403,7 +403,6 @@
    TNLcontext *tnl = TNL_CONTEXT(ctx);
 
    R200_NEWPRIM( rmesa );
-   rmesa->swtcl.vertex_format = 0;
 
    r200ChooseVertexState( ctx );
    r200ChooseRenderState( ctx );
@@ -446,7 +445,6 @@
       rmesa->dma.flush( rmesa );       
 
    rmesa->dma.flush = 0;
-   rmesa->swtcl.vertex_format = 0;
    
    if (rmesa->swtcl.indexed_verts.buf) 
       r200ReleaseDmaRegion( rmesa, &rmesa->swtcl.indexed_verts, 
Index: src/mesa/tnl/t_vertex.h
===================================================================
RCS file: /cvs/mesa/Mesa/src/mesa/tnl/t_vertex.h,v
retrieving revision 1.6
diff -u -d -r1.6 t_vertex.h
--- a/src/mesa/tnl/t_vertex.h   16 Feb 2004 15:15:24 -0000      1.6
+++ b/src/mesa/tnl/t_vertex.h   17 Apr 2004 04:49:55 -0000
@@ -28,6 +28,8 @@
 #ifndef _TNL_VERTEX_H
 #define _TNL_VERTEX_H
 
+#include "mtypes.h"
+
 /* New mechanism to specify hardware vertices so that tnl can build
  * and manipulate them directly.  
  */

Reply via email to