Merge remote branch 'main/master' into radeon-rewrite
[mesa.git] / src / mesa / drivers / dri / r300 / r300_swtcl.c
index d463ab3a2d68483b46e6b77800224dbe3358354f..f57516acf413795dde1d09a0ae7bd158dcd2fd8f 100644 (file)
@@ -56,26 +56,23 @@ USE OR OTHER DEALINGS IN THE SOFTWARE.
 #include "r300_state.h"
 #include "r300_ioctl.h"
 #include "r300_emit.h"
-#include "r300_mem.h"
+#include "r300_tex.h"
 
-static void flush_last_swtcl_prim( r300ContextPtr rmesa  );
-
-
-void r300EmitVertexAOS(r300ContextPtr rmesa, GLuint vertex_size, GLuint offset);
+void r300EmitVertexAOS(r300ContextPtr rmesa, GLuint vertex_size, struct radeon_bo *bo, GLuint offset);
 void r300EmitVbufPrim(r300ContextPtr rmesa, GLuint primitive, GLuint vertex_nr);
 #define EMIT_ATTR( ATTR, STYLE )                                       \
 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++;                                   \
+   rmesa->radeon.swtcl.vertex_attrs[rmesa->radeon.swtcl.vertex_attr_count].attrib = (ATTR);    \
+   rmesa->radeon.swtcl.vertex_attrs[rmesa->radeon.swtcl.vertex_attr_count].format = (STYLE);   \
+   rmesa->radeon.swtcl.vertex_attr_count++;                                    \
 } while (0)
 
 #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++;                                   \
+   rmesa->radeon.swtcl.vertex_attrs[rmesa->radeon.swtcl.vertex_attr_count].attrib = 0;         \
+   rmesa->radeon.swtcl.vertex_attrs[rmesa->radeon.swtcl.vertex_attr_count].format = EMIT_PAD;  \
+   rmesa->radeon.swtcl.vertex_attrs[rmesa->radeon.swtcl.vertex_attr_count].offset = (N);               \
+   rmesa->radeon.swtcl.vertex_attr_count++;                                    \
 } while (0)
 
 static void r300SetVertexFormat( GLcontext *ctx )
@@ -114,7 +111,7 @@ static void r300SetVertexFormat( GLcontext *ctx )
        }
 
        assert( VB->AttribPtr[VERT_ATTRIB_POS] != NULL );
-       rmesa->swtcl.vertex_attr_count = 0;
+       rmesa->radeon.swtcl.vertex_attr_count = 0;
 
        /* EMIT_ATTR's must be in order as they tell t_vertex.c how to
         * build up a hardware vertex.
@@ -266,14 +263,27 @@ static void r300SetVertexFormat( GLcontext *ctx )
        }
 
        R300_NEWPRIM(rmesa);
-       R300_STATECHANGE(rmesa, vir[0]);
-       ((drm_r300_cmd_header_t *) rmesa->hw.vir[0].cmd)->packet0.count =
+       if (rmesa->radeon.radeonScreen->kernel_mm) {
+               R300_STATECHANGE(rmesa, vir[0]);
+               rmesa->hw.vir[0].cmd[0] &= 0xC000FFFF;
+               rmesa->hw.vir[1].cmd[0] &= 0xC000FFFF;
+               rmesa->hw.vir[0].cmd[0] |=
+                       (r300VAPInputRoute0(&rmesa->hw.vir[0].cmd[R300_VIR_CNTL_0],
+                                           VB->AttribPtr, inputs, tab, nr) & 0x3FFF) << 16;
+               R300_STATECHANGE(rmesa, vir[1]);
+               rmesa->hw.vir[1].cmd[0] |=
+                       (r300VAPInputRoute1(&rmesa->hw.vir[1].cmd[R300_VIR_CNTL_0], swizzle,
+                                           nr) & 0x3FFF) << 16;
+       } else {
+               R300_STATECHANGE(rmesa, vir[0]);
+               ((drm_r300_cmd_header_t *) rmesa->hw.vir[0].cmd)->packet0.count =
                r300VAPInputRoute0(&rmesa->hw.vir[0].cmd[R300_VIR_CNTL_0],
                                   VB->AttribPtr, inputs, tab, nr);
-       R300_STATECHANGE(rmesa, vir[1]);
-       ((drm_r300_cmd_header_t *) rmesa->hw.vir[1].cmd)->packet0.count =
+               R300_STATECHANGE(rmesa, vir[1]);
+               ((drm_r300_cmd_header_t *) rmesa->hw.vir[1].cmd)->packet0.count =
                r300VAPInputRoute1(&rmesa->hw.vir[1].cmd[R300_VIR_CNTL_0], swizzle,
                                   nr);
+       }
 
        R300_STATECHANGE(rmesa, vic);
        rmesa->hw.vic.cmd[R300_VIC_CNTL_0] = r300VAPInputCntl0(ctx, InputsRead);
@@ -283,89 +293,20 @@ static void r300SetVertexFormat( GLcontext *ctx )
        rmesa->hw.vof.cmd[R300_VOF_CNTL_0] = r300VAPOutputCntl0(ctx, OutputsWritten);
        rmesa->hw.vof.cmd[R300_VOF_CNTL_1] = vap_fmt_1;
 
-       rmesa->swtcl.vertex_size =
+       rmesa->radeon.swtcl.vertex_size =
                _tnl_install_attrs( ctx,
-                                   rmesa->swtcl.vertex_attrs,
-                                   rmesa->swtcl.vertex_attr_count,
+                                   rmesa->radeon.swtcl.vertex_attrs,
+                                   rmesa->radeon.swtcl.vertex_attr_count,
                                    NULL, 0 );
 
-       rmesa->swtcl.vertex_size /= 4;
+       rmesa->radeon.swtcl.vertex_size /= 4;
 
        RENDERINPUTS_COPY( rmesa->tnl_index_bitset, index_bitset );
 
 
        R300_STATECHANGE(rmesa, vte);
        rmesa->hw.vte.cmd[1] = vte;
-       rmesa->hw.vte.cmd[2] = rmesa->swtcl.vertex_size;
-}
-
-
-/* Flush vertices in the current dma region.
- */
-static void flush_last_swtcl_prim( r300ContextPtr rmesa  )
-{
-       if (RADEON_DEBUG & DEBUG_IOCTL)
-               fprintf(stderr, "%s\n", __FUNCTION__);
-
-       rmesa->dma.flush = NULL;
-
-       if (rmesa->dma.current.buf) {
-               struct r300_dma_region *current = &rmesa->dma.current;
-               GLuint current_offset = GET_START(current);
-
-               assert (current->start +
-                       rmesa->swtcl.numverts * rmesa->swtcl.vertex_size * 4 ==
-                       current->ptr);
-
-               if (rmesa->dma.current.start != rmesa->dma.current.ptr) {
-
-                       r300EnsureCmdBufSpace( rmesa, rmesa->hw.max_state_size + (12*sizeof(int)), __FUNCTION__);
-
-                       r300EmitState(rmesa);
-
-                       r300EmitVertexAOS( rmesa,
-                                          rmesa->swtcl.vertex_size,
-                                          current_offset);
-
-                       r300EmitVbufPrim( rmesa,
-                                         rmesa->swtcl.hw_primitive,
-                                         rmesa->swtcl.numverts);
-
-                       r300EmitCacheFlush(rmesa);
-               }
-
-               rmesa->swtcl.numverts = 0;
-               current->start = current->ptr;
-       }
-}
-
-/* Alloc space in the current dma region.
- */
-static void *
-r300AllocDmaLowVerts( r300ContextPtr rmesa, int nverts, int vsize )
-{
-       GLuint bytes = vsize * nverts;
-
-       if ( rmesa->dma.current.ptr + bytes > rmesa->dma.current.end )
-               r300RefillCurrentDmaRegion( rmesa, bytes);
-
-       if (!rmesa->dma.flush) {
-               rmesa->radeon.glCtx->Driver.NeedFlush |= FLUSH_STORED_VERTICES;
-               rmesa->dma.flush = flush_last_swtcl_prim;
-       }
-
-       ASSERT( vsize == rmesa->swtcl.vertex_size * 4 );
-       ASSERT( rmesa->dma.flush == flush_last_swtcl_prim );
-       ASSERT( rmesa->dma.current.start +
-               rmesa->swtcl.numverts * rmesa->swtcl.vertex_size * 4 ==
-               rmesa->dma.current.ptr );
-
-       {
-               GLubyte *head = (GLubyte *) (rmesa->dma.current.address + rmesa->dma.current.ptr);
-               rmesa->dma.current.ptr += bytes;
-               rmesa->swtcl.numverts += nverts;
-               return head;
-       }
+       rmesa->hw.vte.cmd[2] = rmesa->radeon.swtcl.vertex_size;
 }
 
 static GLuint reduced_prim[] = {
@@ -405,11 +346,11 @@ static void r300RenderPrimitive( GLcontext *ctx, GLenum prim );
 #undef LOCAL_VARS
 #undef ALLOC_VERTS
 #define CTX_ARG r300ContextPtr rmesa
-#define GET_VERTEX_DWORDS() rmesa->swtcl.vertex_size
-#define ALLOC_VERTS( n, size ) r300AllocDmaLowVerts( rmesa, n, size * 4 )
+#define GET_VERTEX_DWORDS() rmesa->radeon.swtcl.vertex_size
+#define ALLOC_VERTS( n, size ) rcommonAllocDmaLowVerts( &rmesa->radeon, n, size * 4 )
 #define LOCAL_VARS                                             \
    r300ContextPtr rmesa = R300_CONTEXT(ctx);           \
-   const char *r300verts = (char *)rmesa->swtcl.verts;
+   const char *r300verts = (char *)rmesa->radeon.swtcl.verts;
 #define VERT(x) (r300Vertex *)(r300verts + ((x) * vertsize * sizeof(int)))
 #define VERTEX r300Vertex
 #define DO_DEBUG_VERTS (1 && (RADEON_DEBUG & DEBUG_VERTS))
@@ -468,7 +409,7 @@ static struct {
 #define VERT_Y(_v) _v->v.y
 #define VERT_Z(_v) _v->v.z
 #define AREA_IS_CCW( a ) (a < 0)
-#define GET_VERTEX(e) (rmesa->swtcl.verts + (e*rmesa->swtcl.vertex_size*sizeof(int)))
+#define GET_VERTEX(e) (rmesa->radeon.swtcl.verts + (e*rmesa->radeon.swtcl.vertex_size*sizeof(int)))
 
 /* Only used to pull back colors into vertices (ie, we know color is
  * floating point).
@@ -514,7 +455,7 @@ do {                                                        \
  ***********************************************************************/
 
 #define RASTERIZE(x) r300RasterPrimitive( ctx, reduced_prim[x] )
-#define RENDER_PRIMITIVE rmesa->swtcl.render_primitive
+#define RENDER_PRIMITIVE rmesa->radeon.swtcl.render_primitive
 #undef TAG
 #define TAG(x) x
 #include "tnl_dd/t_dd_unfilled.h"
@@ -571,8 +512,8 @@ static void init_rast_tab( void )
 #undef LOCAL_VARS
 #define LOCAL_VARS                                             \
    r300ContextPtr rmesa = R300_CONTEXT(ctx);           \
-   const GLuint vertsize = rmesa->swtcl.vertex_size;           \
-   const char *r300verts = (char *)rmesa->swtcl.verts;         \
+   const GLuint vertsize = rmesa->radeon.swtcl.vertex_size;            \
+   const char *r300verts = (char *)rmesa->radeon.swtcl.verts;          \
    const GLuint * const elt = TNL_CONTEXT(ctx)->vb.Elts;       \
    const GLboolean stipple = ctx->Line.StippleFlag;            \
    (void) elt; (void) stipple;
@@ -604,7 +545,7 @@ static void r300ChooseRenderState( GLcontext *ctx )
        if (flags & DD_TRI_LIGHT_TWOSIDE) index |= R300_TWOSIDE_BIT;
        if (flags & DD_TRI_UNFILLED)      index |= R300_UNFILLED_BIT;
 
-       if (index != rmesa->swtcl.RenderIndex) {
+       if (index != rmesa->radeon.swtcl.RenderIndex) {
                tnl->Driver.Render.Points = rast_tab[index].points;
                tnl->Driver.Render.Line = rast_tab[index].line;
                tnl->Driver.Render.ClippedLine = rast_tab[index].line;
@@ -621,7 +562,7 @@ static void r300ChooseRenderState( GLcontext *ctx )
                        tnl->Driver.Render.ClippedPolygon = _tnl_RenderClippedPolygon;
                }
 
-               rmesa->swtcl.RenderIndex = index;
+               rmesa->radeon.swtcl.RenderIndex = index;
        }
 }
 
@@ -634,14 +575,17 @@ static void r300RenderStart(GLcontext *ctx)
        r300ChooseRenderState(ctx);
        r300SetVertexFormat(ctx);
 
+       r300ValidateBuffers(ctx);
+
        r300UpdateShaders(rmesa);
        r300UpdateShaderStates(rmesa);
 
        r300EmitCacheFlush(rmesa);
 
-       if (rmesa->dma.flush != 0 &&
-           rmesa->dma.flush != flush_last_swtcl_prim)
-               rmesa->dma.flush( rmesa );
+       /* investigate if we can put back flush optimisation if needed */
+       if (rmesa->radeon.dma.flush != NULL) {
+               rmesa->radeon.dma.flush(ctx);
+       }
 
 }
 
@@ -653,9 +597,9 @@ static void r300RasterPrimitive( GLcontext *ctx, GLuint hwprim )
 {
        r300ContextPtr rmesa = R300_CONTEXT(ctx);
 
-       if (rmesa->swtcl.hw_primitive != hwprim) {
+       if (rmesa->radeon.swtcl.hw_primitive != hwprim) {
                R300_NEWPRIM( rmesa );
-               rmesa->swtcl.hw_primitive = hwprim;
+               rmesa->radeon.swtcl.hw_primitive = hwprim;
        }
 }
 
@@ -663,7 +607,7 @@ static void r300RenderPrimitive(GLcontext *ctx, GLenum prim)
 {
 
        r300ContextPtr rmesa = R300_CONTEXT(ctx);
-       rmesa->swtcl.render_primitive = prim;
+       rmesa->radeon.swtcl.render_primitive = prim;
 
        if ((prim == GL_TRIANGLES) && (ctx->_TriangleCaps & DD_TRI_UNFILLED))
          return;
@@ -702,10 +646,10 @@ void r300InitSwtcl(GLcontext *ctx)
        _tnl_init_vertices( ctx, ctx->Const.MaxArrayLockSize + 12,
                            48 * 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;
+       rmesa->radeon.swtcl.verts = (GLubyte *)tnl->clipspace.vertex_buf;
+       rmesa->radeon.swtcl.RenderIndex = ~0;
+       rmesa->radeon.swtcl.render_primitive = GL_TRIANGLES;
+       rmesa->radeon.swtcl.hw_primitive = 0;
 
        _tnl_invalidate_vertex_state( ctx, ~0 );
        _tnl_invalidate_vertices( ctx, ~0 );
@@ -724,33 +668,52 @@ void r300DestroySwtcl(GLcontext *ctx)
 {
 }
 
-void r300EmitVertexAOS(r300ContextPtr rmesa, GLuint vertex_size, GLuint offset)
+void r300EmitVertexAOS(r300ContextPtr rmesa, GLuint vertex_size, struct radeon_bo *bo, GLuint offset)
 {
-       int cmd_reserved = 0;
-       int cmd_written = 0;
+       BATCH_LOCALS(&rmesa->radeon);
 
-       drm_radeon_cmd_header_t *cmd = NULL;
        if (RADEON_DEBUG & DEBUG_VERTS)
-         fprintf(stderr, "%s:  vertex_size %d, offset 0x%x \n",
-                 __FUNCTION__, vertex_size, offset);
-
-       start_packet3(CP_PACKET3(R300_PACKET3_3D_LOAD_VBPNTR, 2), 2);
-       e32(1);
-       e32(vertex_size | (vertex_size << 8));
-       e32(offset);
+               fprintf(stderr, "%s:  vertex_size %d, offset 0x%x \n",
+                       __FUNCTION__, vertex_size, offset);
+
+       BEGIN_BATCH(7);
+       OUT_BATCH_PACKET3(R300_PACKET3_3D_LOAD_VBPNTR, 2);
+       OUT_BATCH(1);
+       OUT_BATCH(vertex_size | (vertex_size << 8));
+       OUT_BATCH_RELOC(offset, bo, offset, RADEON_GEM_DOMAIN_GTT, 0, 0);
+       END_BATCH();
 }
 
 void r300EmitVbufPrim(r300ContextPtr rmesa, GLuint primitive, GLuint vertex_nr)
 {
-
-       int cmd_reserved = 0;
-       int cmd_written = 0;
+       BATCH_LOCALS(&rmesa->radeon);
        int type, num_verts;
-       drm_radeon_cmd_header_t *cmd = NULL;
 
        type = r300PrimitiveType(rmesa, primitive);
        num_verts = r300NumVerts(rmesa, vertex_nr, primitive);
 
-       start_packet3(CP_PACKET3(R300_PACKET3_3D_DRAW_VBUF_2, 0), 0);
-       e32(R300_VAP_VF_CNTL__PRIM_WALK_VERTEX_LIST | (num_verts << 16) | type);
+       BEGIN_BATCH(3);
+       OUT_BATCH_PACKET3(R300_PACKET3_3D_DRAW_VBUF_2, 0);
+       OUT_BATCH(R300_VAP_VF_CNTL__PRIM_WALK_VERTEX_LIST | (num_verts << 16) | type);
+       END_BATCH();
+}
+
+void r300_swtcl_flush(GLcontext *ctx, uint32_t current_offset)
+{
+  r300ContextPtr rmesa = R300_CONTEXT(ctx);
+
+  rcommonEnsureCmdBufSpace(&rmesa->radeon,
+                          rmesa->radeon.hw.max_state_size + (12*sizeof(int)),
+                          __FUNCTION__);
+  radeonEmitState(&rmesa->radeon);
+  r300EmitVertexAOS(rmesa,
+                   rmesa->radeon.swtcl.vertex_size,
+                   rmesa->radeon.dma.current,
+                   current_offset);
+  
+  r300EmitVbufPrim(rmesa,
+                  rmesa->radeon.swtcl.hw_primitive,
+                  rmesa->radeon.swtcl.numverts);
+  r300EmitCacheFlush(rmesa);
+  COMMIT_BATCH();
 }