[Mesa-dev] [PATCH] draw: add support for later transform feedback extensions

Jose Fonseca jfonseca at vmware.com
Tue Dec 18 09:23:20 PST 2012


I'm not very familiar with these features, but if this passes piglit tests then it sounds good to me FWIW.

It's however weird that using draw->pt.max_index + 1 (i.e., maximum fecthed vertex) for count_from_stream_output works in general. I'd imagine it to be some sort of runtime determined amount (which would  depend among other things on the bound geometry shader).

Jose

----- Original Message -----
> This adds support to draw for the new features of transform feedback.
> 
> a) fix count_from_stream_output, using max_index+1 for now but it
> looks
> like it should be valid as its derived from the vertex elements/vbo.
> 
> b) fix striding and dst offsets in output buffers - was just wrong
> before.
> 
> c) fix crash if tfb is suspended (so.num_targets == 0)
> 
> This also enables the new features on softpipe. It should be possible
> to enable them on llvmpipe as well after this commit, but would need
> to schedule piglit runs.
> 
> Signed-off-by: Dave Airlie <airlied at redhat.com>
> ---
>  src/gallium/auxiliary/draw/draw_pt.c         |  9 +++++++--
>  src/gallium/auxiliary/draw/draw_pt_so_emit.c | 12 +++++++++---
>  src/gallium/drivers/softpipe/sp_screen.c     |  2 +-
>  3 files changed, 17 insertions(+), 6 deletions(-)
> 
> diff --git a/src/gallium/auxiliary/draw/draw_pt.c
> b/src/gallium/auxiliary/draw/draw_pt.c
> index ddaedcd..50b9efa 100644
> --- a/src/gallium/auxiliary/draw/draw_pt.c
> +++ b/src/gallium/auxiliary/draw/draw_pt.c
> @@ -464,7 +464,7 @@ draw_vbo(struct draw_context *draw,
>  {
>     unsigned instance;
>     unsigned index_limit;
> -
> +   unsigned count;
>     assert(info->instance_count > 0);
>     if (info->indexed)
>        assert(draw->pt.user.elts);
> @@ -518,6 +518,11 @@ draw_vbo(struct draw_context *draw,
>  
>     draw->pt.max_index = index_limit - 1;
>  
> +   count = info->count;
> +   if (count == 0) {
> +      if (info->count_from_stream_output)
> +         count = draw->pt.max_index + 1;
> +   }
>  
>     /*
>      * TODO: We could use draw->pt.max_index to further narrow
> @@ -531,7 +536,7 @@ draw_vbo(struct draw_context *draw,
>           draw_pt_arrays_restart(draw, info);
>        }
>        else {
> -         draw_pt_arrays(draw, info->mode, info->start, info->count);
> +         draw_pt_arrays(draw, info->mode, info->start, count);
>        }
>     }
>  }
> diff --git a/src/gallium/auxiliary/draw/draw_pt_so_emit.c
> b/src/gallium/auxiliary/draw/draw_pt_so_emit.c
> index ecf287f..80a164a 100644
> --- a/src/gallium/auxiliary/draw/draw_pt_so_emit.c
> +++ b/src/gallium/auxiliary/draw/draw_pt_so_emit.c
> @@ -118,6 +118,7 @@ static void so_emit_prim(struct pt_so_emit *so,
>     for (i = 0; i < num_vertices; ++i) {
>        const float (*input)[4];
>        unsigned total_written_compos = 0;
> +      int ob;
>        /*debug_printf("%d) vertex index = %d (prim idx = %d)\n", i,
>        indices[i], prim_idx);*/
>        input = (const float (*)[4])(
>           (const char *)input_ptr + (indices[i] *
>           input_vertex_stride));
> @@ -126,15 +127,17 @@ static void so_emit_prim(struct pt_so_emit *so,
>           unsigned idx = state->output[slot].register_index;
>           unsigned start_comp = state->output[slot].start_component;
>           unsigned num_comps = state->output[slot].num_components;
> -         int ob = state->output[slot].output_buffer;
> +
> +         ob = state->output[slot].output_buffer;
>  
>           buffer = (float *)((char *)draw->so.targets[ob]->mapping +
>                              draw->so.targets[ob]->target.buffer_offset
>                              +
> -                            draw->so.targets[ob]->internal_offset);
> +                            draw->so.targets[ob]->internal_offset) +
> state->output[slot].dst_offset;
>           memcpy(buffer, &input[idx][start_comp], num_comps *
>           sizeof(float));
> -         draw->so.targets[ob]->internal_offset += num_comps *
> sizeof(float);
>           total_written_compos += num_comps;
>        }
> +      for (ob = 0; ob < draw->so.num_targets; ++ob)
> +         draw->so.targets[ob]->internal_offset += state->stride[ob]
> * sizeof(float);
>     }
>     so->emitted_vertices += num_vertices;
>     ++so->emitted_primitives;
> @@ -193,6 +196,9 @@ void draw_pt_so_emit( struct pt_so_emit *emit,
>     if (!emit->has_so)
>        return;
>  
> +   if (!draw->so.num_targets)
> +      return;
> +
>     emit->emitted_vertices = 0;
>     emit->emitted_primitives = 0;
>     emit->generated_primitives = 0;
> diff --git a/src/gallium/drivers/softpipe/sp_screen.c
> b/src/gallium/drivers/softpipe/sp_screen.c
> index 564da5e..840cff6 100644
> --- a/src/gallium/drivers/softpipe/sp_screen.c
> +++ b/src/gallium/drivers/softpipe/sp_screen.c
> @@ -155,10 +155,10 @@ softpipe_get_param(struct pipe_screen *screen,
> enum pipe_cap param)
>     case PIPE_CAP_USER_VERTEX_BUFFERS:
>     case PIPE_CAP_USER_INDEX_BUFFERS:
>     case PIPE_CAP_USER_CONSTANT_BUFFERS:
> +   case PIPE_CAP_STREAM_OUTPUT_PAUSE_RESUME:
>        return 1;
>     case PIPE_CAP_CONSTANT_BUFFER_OFFSET_ALIGNMENT:
>        return 16;
> -   case PIPE_CAP_STREAM_OUTPUT_PAUSE_RESUME:
>     case PIPE_CAP_TGSI_CAN_COMPACT_VARYINGS:
>     case PIPE_CAP_TGSI_CAN_COMPACT_CONSTANTS:
>     case PIPE_CAP_VERTEX_BUFFER_OFFSET_4BYTE_ALIGNED_ONLY:
> --
> 1.8.0.1
> 
> _______________________________________________
> mesa-dev mailing list
> mesa-dev at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/mesa-dev
> 


More information about the mesa-dev mailing list