diff options
-rw-r--r-- | src/gallium/auxiliary/draw/draw_pipe.c | 74 | ||||
-rw-r--r-- | src/gallium/auxiliary/draw/draw_pt_decompose.h | 153 | ||||
-rw-r--r-- | src/gallium/auxiliary/draw/draw_pt_varray.c | 11 | ||||
-rw-r--r-- | src/gallium/auxiliary/draw/draw_pt_vcache.c | 117 |
4 files changed, 263 insertions, 92 deletions
diff --git a/src/gallium/auxiliary/draw/draw_pipe.c b/src/gallium/auxiliary/draw/draw_pipe.c index cb97f955b29..1d26706deee 100644 --- a/src/gallium/auxiliary/draw/draw_pipe.c +++ b/src/gallium/auxiliary/draw/draw_pipe.c @@ -212,6 +212,55 @@ void draw_pipeline_run( struct draw_context *draw, draw->pipeline.vertex_count = 0; } +#define QUAD(i0,i1,i2,i3) \ + do_triangle( draw, \ + ( DRAW_PIPE_RESET_STIPPLE | \ + DRAW_PIPE_EDGE_FLAG_0 | \ + DRAW_PIPE_EDGE_FLAG_2 ), \ + verts + stride * ((i0) & ~DRAW_PIPE_FLAG_MASK), \ + verts + stride * (i1), \ + verts + stride * (i3)); \ + do_triangle( draw, \ + ( DRAW_PIPE_EDGE_FLAG_0 | \ + DRAW_PIPE_EDGE_FLAG_1 ), \ + verts + stride * ((i1) & ~DRAW_PIPE_FLAG_MASK), \ + verts + stride * (i2), \ + verts + stride * (i3)) + +#define TRIANGLE(flags,i0,i1,i2) \ + do_triangle( draw, \ + flags, /* flags */ \ + verts + stride * ((i0) & ~DRAW_PIPE_FLAG_MASK), \ + verts + stride * (i1), \ + verts + stride * (i2)) + +#define LINE(flags,i0,i1) \ + do_line( draw, \ + flags, \ + verts + stride * ((i0) & ~DRAW_PIPE_FLAG_MASK), \ + verts + stride * (i+1)) + +#define POINT(i0) \ + do_point( draw, \ + verts + stride * i0 ) + +#define FUNC pipe_run_linear +#define ARGS \ + struct draw_context *draw, \ + unsigned prim, \ + struct vertex_header *vertices, \ + unsigned stride + +#define LOCAL_VARS \ + char *verts = (char *)vertices; \ + boolean flatfirst = (draw->rasterizer->flatshade && \ + draw->rasterizer->flatshade_first); \ + unsigned i, flags + +#define FLUSH + +#include "draw_pt_decompose.h" + void draw_pipeline_run_linear( struct draw_context *draw, unsigned prim, struct vertex_header *vertices, @@ -219,34 +268,11 @@ void draw_pipeline_run_linear( struct draw_context *draw, unsigned stride ) { char *verts = (char *)vertices; - unsigned i; - draw->pipeline.verts = verts; draw->pipeline.vertex_stride = stride; draw->pipeline.vertex_count = count; - switch (prim) { - case PIPE_PRIM_POINTS: - for (i = 0; i < count; i++) - do_point( draw, - verts + stride * i ); - break; - case PIPE_PRIM_LINES: - for (i = 0; i+1 < count; i += 2) - do_line( draw, - i+0, /* flags */ - verts + stride * ((i+0) & ~DRAW_PIPE_FLAG_MASK), - verts + stride * (i+1)); - break; - case PIPE_PRIM_TRIANGLES: - for (i = 0; i+2 < count; i += 3) - do_triangle( draw, - (i+0), /* flags */ - verts + stride * ((i+0) & ~DRAW_PIPE_FLAG_MASK), - verts + stride * (i+1), - verts + stride * (i+2)); - break; - } + pipe_run_linear(draw, prim, vertices, stride, count); draw->pipeline.verts = NULL; draw->pipeline.vertex_count = 0; diff --git a/src/gallium/auxiliary/draw/draw_pt_decompose.h b/src/gallium/auxiliary/draw/draw_pt_decompose.h new file mode 100644 index 00000000000..dccfde99dde --- /dev/null +++ b/src/gallium/auxiliary/draw/draw_pt_decompose.h @@ -0,0 +1,153 @@ + + +static void FUNC( ARGS, + unsigned count ) +{ + LOCAL_VARS; + + switch (prim) { + case PIPE_PRIM_POINTS: + for (i = 0; i < count; i ++) { + POINT( (i + 0) ); + } + break; + + case PIPE_PRIM_LINES: + for (i = 0; i+1 < count; i += 2) { + LINE( DRAW_PIPE_RESET_STIPPLE, + (i + 0), + (i + 1)); + } + break; + + case PIPE_PRIM_LINE_LOOP: + if (count >= 2) { + flags = DRAW_PIPE_RESET_STIPPLE; + + for (i = 1; i < count; i++, flags = 0) { + LINE( flags, + (i - 1), + (i )); + } + + LINE( flags, + (i - 1), + (0 )); + } + break; + + case PIPE_PRIM_LINE_STRIP: + flags = DRAW_PIPE_RESET_STIPPLE; + for (i = 1; i < count; i++, flags = 0) { + LINE( flags, + (i - 1), + (i )); + } + break; + + case PIPE_PRIM_TRIANGLES: + for (i = 0; i+2 < count; i += 3) { + TRIANGLE( DRAW_PIPE_RESET_STIPPLE | DRAW_PIPE_EDGE_FLAG_ALL, + (i + 0), + (i + 1), + (i + 2 )); + } + break; + + case PIPE_PRIM_TRIANGLE_STRIP: + if (flatfirst) { + for (i = 0; i+2 < count; i++) { + TRIANGLE( DRAW_PIPE_RESET_STIPPLE | DRAW_PIPE_EDGE_FLAG_ALL, + (i + 0), + (i + 1 + (i&1)), + (i + 2 - (i&1))); + } + } + else { + for (i = 0; i+2 < count; i++) { + TRIANGLE( DRAW_PIPE_RESET_STIPPLE | DRAW_PIPE_EDGE_FLAG_ALL, + (i + 0 + (i&1)), + (i + 1 - (i&1)), + (i + 2 )); + } + } + break; + + case PIPE_PRIM_TRIANGLE_FAN: + if (count >= 3) { + if (flatfirst) { + for (i = 0; i+2 < count; i++) { + TRIANGLE( DRAW_PIPE_RESET_STIPPLE | DRAW_PIPE_EDGE_FLAG_ALL, + (i + 1), + (i + 2), + (0 )); + } + } + else { + for (i = 0; i+2 < count; i++) { + TRIANGLE( DRAW_PIPE_RESET_STIPPLE | DRAW_PIPE_EDGE_FLAG_ALL, + (0), + (i + 1), + (i + 2 )); + } + } + } + break; + + + case PIPE_PRIM_QUADS: + for (i = 0; i+3 < count; i += 4) { + QUAD( (i + 0), + (i + 1), + (i + 2), + (i + 3)); + } + break; + + case PIPE_PRIM_QUAD_STRIP: + for (i = 0; i+3 < count; i += 2) { + QUAD( (i + 2), + (i + 0), + (i + 1), + (i + 3)); + } + break; + + case PIPE_PRIM_POLYGON: + { + /* These bitflags look a little odd because we submit the + * vertices as (1,2,0) to satisfy flatshade requirements. + */ + const unsigned edge_first = DRAW_PIPE_EDGE_FLAG_2; + const unsigned edge_middle = DRAW_PIPE_EDGE_FLAG_0; + const unsigned edge_last = DRAW_PIPE_EDGE_FLAG_1; + + flags = DRAW_PIPE_RESET_STIPPLE | edge_first | edge_middle; + + for (i = 0; i+2 < count; i++, flags = edge_middle) { + + if (i + 3 == count) + flags |= edge_last; + + TRIANGLE( flags, + (i + 1), + (i + 2), + (0)); + } + } + break; + + default: + assert(0); + break; + } + + FLUSH; +} + + +#undef TRIANGLE +#undef QUAD +#undef POINT +#undef LINE +#undef FUNC diff --git a/src/gallium/auxiliary/draw/draw_pt_varray.c b/src/gallium/auxiliary/draw/draw_pt_varray.c index af6e2d51578..06fd866ccd0 100644 --- a/src/gallium/auxiliary/draw/draw_pt_varray.c +++ b/src/gallium/auxiliary/draw/draw_pt_varray.c @@ -141,14 +141,19 @@ static INLINE void varray_point( struct varray_frontend *varray, } - +#if 0 +#define TRIANGLE(flags,i0,i1,i2) varray_triangle(varray,i0,i1,i2) +#define LINE(flags,i0,i1) varray_line(varray,i0,i1) +#define POINT(i0) varray_point(varray,i0) +#define FUNC varray_decompose +#include "draw_pt_decompose.h" +#else #define TRIANGLE(vc,i0,i1,i2) varray_triangle(vc,i0,i1,i2) #define LINE(vc,i0,i1) varray_line(vc,i0,i1) #define POINT(vc,i0) varray_point(vc,i0) #define FUNC varray_run #include "draw_pt_varray_tmp_linear.h" - - +#endif static unsigned decompose_prim[PIPE_PRIM_POLYGON + 1] = { PIPE_PRIM_POINTS, diff --git a/src/gallium/auxiliary/draw/draw_pt_vcache.c b/src/gallium/auxiliary/draw/draw_pt_vcache.c index a3495f2a30c..6c17edba340 100644 --- a/src/gallium/auxiliary/draw/draw_pt_vcache.c +++ b/src/gallium/auxiliary/draw/draw_pt_vcache.c @@ -104,23 +104,11 @@ static INLINE void vcache_elt( struct vcache_frontend *vcache, static void vcache_triangle( struct vcache_frontend *vcache, + ushort flags, unsigned i0, unsigned i1, unsigned i2 ) { - vcache_elt(vcache, i0, 0); - vcache_elt(vcache, i1, 0); - vcache_elt(vcache, i2, 0); - vcache_check_flush(vcache); -} - - -static void vcache_triangle_flags( struct vcache_frontend *vcache, - ushort flags, - unsigned i0, - unsigned i1, - unsigned i2 ) -{ vcache_elt(vcache, i0, flags); vcache_elt(vcache, i1, 0); vcache_elt(vcache, i2, 0); @@ -128,20 +116,10 @@ static void vcache_triangle_flags( struct vcache_frontend *vcache, } static void vcache_line( struct vcache_frontend *vcache, + ushort flags, unsigned i0, unsigned i1 ) { - vcache_elt(vcache, i0, 0); - vcache_elt(vcache, i1, 0); - vcache_check_flush(vcache); -} - - -static void vcache_line_flags( struct vcache_frontend *vcache, - ushort flags, - unsigned i0, - unsigned i1 ) -{ vcache_elt(vcache, i0, flags); vcache_elt(vcache, i1, 0); vcache_check_flush(vcache); @@ -161,46 +139,63 @@ static void vcache_quad( struct vcache_frontend *vcache, unsigned i2, unsigned i3 ) { - vcache_triangle( vcache, i0, i1, i3 ); - vcache_triangle( vcache, i1, i2, i3 ); -} - -static void vcache_ef_quad( struct vcache_frontend *vcache, - unsigned i0, - unsigned i1, - unsigned i2, - unsigned i3 ) -{ - const unsigned omitEdge1 = DRAW_PIPE_EDGE_FLAG_0 | DRAW_PIPE_EDGE_FLAG_2; - const unsigned omitEdge2 = DRAW_PIPE_EDGE_FLAG_0 | DRAW_PIPE_EDGE_FLAG_1; - - vcache_triangle_flags( vcache, - DRAW_PIPE_RESET_STIPPLE | omitEdge1, - i0, i1, i3 ); - - vcache_triangle_flags( vcache, - omitEdge2, - i1, i2, i3 ); + vcache_triangle( vcache, + ( DRAW_PIPE_RESET_STIPPLE | + DRAW_PIPE_EDGE_FLAG_0 | + DRAW_PIPE_EDGE_FLAG_2 ), + i0, i1, i3 ); + + vcache_triangle( vcache, + ( DRAW_PIPE_EDGE_FLAG_0 | + DRAW_PIPE_EDGE_FLAG_1 ), + i1, i2, i3 ); } /* At least for now, we're back to using a template include file for * this. The two paths aren't too different though - it may be * possible to reunify them. */ -#define TRIANGLE(vc,flags,i0,i1,i2) vcache_triangle_flags(vc,flags,i0,i1,i2) -#define QUAD(vc,i0,i1,i2,i3) vcache_ef_quad(vc,i0,i1,i2,i3) -#define LINE(vc,flags,i0,i1) vcache_line_flags(vc,flags,i0,i1) -#define POINT(vc,i0) vcache_point(vc,i0) -#define FUNC vcache_run_extras -#include "draw_pt_vcache_tmp.h" - -#define TRIANGLE(vc,flags,i0,i1,i2) vcache_triangle(vc,i0,i1,i2) -#define QUAD(vc,i0,i1,i2,i3) vcache_quad(vc,i0,i1,i2,i3) -#define LINE(vc,flags,i0,i1) vcache_line(vc,i0,i1) -#define POINT(vc,i0) vcache_point(vc,i0) +#define TRIANGLE(flags,i0,i1,i2) \ + vcache_triangle(vcache, \ + flags, \ + get_elt(elts,i0), \ + get_elt(elts,i1), \ + get_elt(elts,i2)) + +#define QUAD(i0,i1,i2,i3) \ + vcache_quad(vcache, \ + get_elt(elts,i0), \ + get_elt(elts,i1), \ + get_elt(elts,i2), \ + get_elt(elts,i3)) + +#define LINE(flags,i0,i1) \ + vcache_line(vcache, \ + flags, \ + get_elt(elts,i0), \ + get_elt(elts,i1)) + +#define POINT(i0) \ + vcache_point(vcache, \ + get_elt(elts,i0)) + #define FUNC vcache_run -#include "draw_pt_vcache_tmp.h" +#define ARGS \ + struct draw_pt_front_end *frontend, \ + pt_elt_func get_elt, \ + const void *elts + +#define LOCAL_VARS \ + struct vcache_frontend *vcache = (struct vcache_frontend *)frontend; \ + struct draw_context *draw = vcache->draw; \ + boolean flatfirst = (draw->rasterizer->flatshade && \ + draw->rasterizer->flatshade_first); \ + unsigned prim = vcache->input_prim; \ + unsigned i, flags; +#define FLUSH vcache_flush( vcache ) + +#include "draw_pt_decompose.h" @@ -213,15 +208,7 @@ static void vcache_prepare( struct draw_pt_front_end *frontend, { struct vcache_frontend *vcache = (struct vcache_frontend *)frontend; - if (opt & PT_PIPELINE) - { - vcache->base.run = vcache_run_extras; - } - else - { - vcache->base.run = vcache_run; - } - + vcache->base.run = vcache_run; vcache->input_prim = prim; vcache->output_prim = draw_pt_reduced_prim(prim); |