diff options
Diffstat (limited to 'src/gallium')
| -rw-r--r-- | src/gallium/auxiliary/draw/draw_pt.c | 86 | ||||
| -rw-r--r-- | src/gallium/docs/source/context.rst | 9 | ||||
| -rw-r--r-- | src/gallium/drivers/llvmpipe/lp_screen.c | 2 | ||||
| -rw-r--r-- | src/gallium/drivers/softpipe/sp_screen.c | 2 | ||||
| -rw-r--r-- | src/gallium/include/pipe/p_defines.h | 1 | ||||
| -rw-r--r-- | src/gallium/include/pipe/p_state.h | 6 | 
6 files changed, 105 insertions, 1 deletions
| diff --git a/src/gallium/auxiliary/draw/draw_pt.c b/src/gallium/auxiliary/draw/draw_pt.c index f44bf2507c..4078b2a07d 100644 --- a/src/gallium/auxiliary/draw/draw_pt.c +++ b/src/gallium/auxiliary/draw/draw_pt.c @@ -287,6 +287,84 @@ draw_print_arrays(struct draw_context *draw, uint prim, int start, uint count)  } +/** Helper code for below */ +#define PRIM_RESTART_LOOP(elements) \ +   do { \ +      for (i = start; i < end; i++) { \ +         if (elements[i] == info->restart_index) { \ +            if (cur_count > 0) { \ +               /* draw elts up to prev pos */ \ +               draw_pt_arrays(draw, prim, cur_start, cur_count); \ +            } \ +            /* begin new prim at next elt */ \ +            cur_start = i + 1; \ +            cur_count = 0; \ +         } \ +         else { \ +            cur_count++; \ +         } \ +      } \ +      if (cur_count > 0) { \ +         draw_pt_arrays(draw, prim, cur_start, cur_count); \ +      } \ +   } while (0) + + +/** + * For drawing prims with primitive restart enabled. + * Scan for restart indexes and draw the runs of elements/vertices between + * the restarts. + */ +static void +draw_pt_arrays_restart(struct draw_context *draw, +                       const struct pipe_draw_info *info) +{ +   const unsigned prim = info->mode; +   const unsigned start = info->start; +   const unsigned count = info->count; +   const unsigned end = start + count; +   unsigned i, cur_start, cur_count; + +   assert(info->primitive_restart); + +   if (draw->pt.user.elts) { +      /* indexed prims (draw_elements) */ +      cur_start = start; +      cur_count = 0; + +      switch (draw->pt.user.eltSize) { +      case 1: +         { +            const ubyte *elt_ub = (const ubyte *) draw->pt.user.elts; +            PRIM_RESTART_LOOP(elt_ub); +         } +         break; +      case 2: +         { +            const ushort *elt_us = (const ushort *) draw->pt.user.elts; +            PRIM_RESTART_LOOP(elt_us); +         } +         break; +      case 4: +         { +            const uint *elt_ui = (const uint *) draw->pt.user.elts; +            PRIM_RESTART_LOOP(elt_ui); +         } +         break; +      default: +         assert(0 && "bad eltSize in draw_arrays()"); +      } +   } +   else { +      /* Non-indexed prims (draw_arrays). +       * Primitive restart should have been handled in the state tracker. +       */ +      draw_pt_arrays(draw, prim, start, count); +   } +} + + +  /**   * Non-instanced drawing.   * \sa draw_arrays_instanced @@ -395,6 +473,12 @@ draw_vbo(struct draw_context *draw,     for (instance = 0; instance < info->instance_count; instance++) {        draw->instance_id = instance + info->start_instance; -      draw_pt_arrays(draw, info->mode, info->start, info->count); + +      if (info->primitive_restart) { +         draw_pt_arrays_restart(draw, info); +      } +      else { +         draw_pt_arrays(draw, info->mode, info->start, info->count); +      }     }  } diff --git a/src/gallium/docs/source/context.rst b/src/gallium/docs/source/context.rst index 5342fc25dc..e09a1304c4 100644 --- a/src/gallium/docs/source/context.rst +++ b/src/gallium/docs/source/context.rst @@ -156,6 +156,15 @@ If there is an index buffer bound, and ``indexed`` field is true, all vertex  indices will be looked up in the index buffer.  ``min_index``, ``max_index``,  and ``index_bias`` apply after index lookup. +When drawing indexed primitives, the primitive restart index can be +used to draw disjoint primitive strips.  For example, several separate +line strips can be drawn by designating a special index value as the +restart index.  The ``primitive_restart`` flag enables/disables this +feature.  The ``restart_index`` field specifies the restart index value. + +When primitive restart is in use, array indexes are compared to the +restart index before adding the index_bias offset. +  If a given vertex element has ``instance_divisor`` set to 0, it is said  it contains per-vertex data and effective vertex attribute address needs  to be recalculated for every index. diff --git a/src/gallium/drivers/llvmpipe/lp_screen.c b/src/gallium/drivers/llvmpipe/lp_screen.c index 96633d9365..ad0ea75b3a 100644 --- a/src/gallium/drivers/llvmpipe/lp_screen.c +++ b/src/gallium/drivers/llvmpipe/lp_screen.c @@ -158,6 +158,8 @@ llvmpipe_get_param(struct pipe_screen *screen, enum pipe_cap param)     case PIPE_CAP_TGSI_FS_COORD_ORIGIN_LOWER_LEFT:     case PIPE_CAP_TGSI_FS_COORD_PIXEL_CENTER_HALF_INTEGER:        return 0; +   case PIPE_CAP_PRIMITIVE_RESTART: +      return 1;     case PIPE_CAP_DEPTHSTENCIL_CLEAR_SEPARATE:        return 1;     case PIPE_CAP_DEPTH_CLAMP: diff --git a/src/gallium/drivers/softpipe/sp_screen.c b/src/gallium/drivers/softpipe/sp_screen.c index 37557d1194..a2bfa1bd8d 100644 --- a/src/gallium/drivers/softpipe/sp_screen.c +++ b/src/gallium/drivers/softpipe/sp_screen.c @@ -112,6 +112,8 @@ softpipe_get_param(struct pipe_screen *screen, enum pipe_cap param)        return 1;     case PIPE_CAP_STREAM_OUTPUT:        return 1; +   case PIPE_CAP_PRIMITIVE_RESTART: +      return 1;     case PIPE_CAP_DEPTHSTENCIL_CLEAR_SEPARATE:        return 0;     case PIPE_CAP_SHADER_STENCIL_EXPORT: diff --git a/src/gallium/include/pipe/p_defines.h b/src/gallium/include/pipe/p_defines.h index b6894c09e8..53f7b601ad 100644 --- a/src/gallium/include/pipe/p_defines.h +++ b/src/gallium/include/pipe/p_defines.h @@ -452,6 +452,7 @@ enum pipe_cap {     PIPE_CAP_BLEND_EQUATION_SEPARATE,     PIPE_CAP_SM3,  /*< Shader Model, supported */     PIPE_CAP_STREAM_OUTPUT, +   PIPE_CAP_PRIMITIVE_RESTART,     /** Maximum texture image units accessible from vertex and fragment shaders      * combined */     PIPE_CAP_MAX_COMBINED_SAMPLERS, diff --git a/src/gallium/include/pipe/p_state.h b/src/gallium/include/pipe/p_state.h index 9a2b31da50..fc6dba346d 100644 --- a/src/gallium/include/pipe/p_state.h +++ b/src/gallium/include/pipe/p_state.h @@ -457,6 +457,12 @@ struct pipe_draw_info     int index_bias; /**< a bias to be added to each index */     unsigned min_index; /**< the min index */     unsigned max_index; /**< the max index */ + +   /** +    * Primitive restart enable/index (only applies to indexed drawing) +    */ +   boolean primitive_restart; +   unsigned restart_index;  }; | 
