Mesa (master): mesa/es3: Add support for GL_PRIMITIVE_RESTART_FIXED_INDEX

Ian Romanick idr at kemper.freedesktop.org
Fri Jan 11 19:19:39 UTC 2013


Module: Mesa
Branch: master
Commit: 42ed81a7c3eec215a543c47239cc30536f284ada
URL:    http://cgit.freedesktop.org/mesa/mesa/commit/?id=42ed81a7c3eec215a543c47239cc30536f284ada

Author: Ian Romanick <ian.d.romanick at intel.com>
Date:   Fri Aug 10 22:28:27 2012 -0700

mesa/es3: Add support for GL_PRIMITIVE_RESTART_FIXED_INDEX

This requires some derived state.  The cut vertex used is either the
value specified by glPrimitiveRestartIndex or it's hard-coded to ~0.
The derived state gl_array_attrib::_RestartIndex captures this value.
In addition, the derived state gl_array_attrib::_PrimitiveRestart is set
whenever either gl_array_attrib::PrimitiveRestart or
gl_array_attrib::PrimitiveRestartFixedIndex is set.

v2: Use _mesa_is_gles3.

Signed-off-by: Ian Romanick <ian.d.romanick at intel.com>

---

 src/mesa/drivers/dri/i965/brw_primitive_restart.c |    8 ++--
 src/mesa/main/api_arrayelt.c                      |    2 +-
 src/mesa/main/attrib.c                            |    3 ++
 src/mesa/main/enable.c                            |   33 +++++++++++++++++++++
 src/mesa/main/mtypes.h                            |   13 +++++++-
 src/mesa/main/varray.c                            |    5 ++-
 src/mesa/state_tracker/st_draw.c                  |    4 +-
 src/mesa/vbo/vbo_exec_array.c                     |   16 +++++-----
 src/mesa/vbo/vbo_primitive_restart.c              |    2 +-
 9 files changed, 67 insertions(+), 19 deletions(-)

diff --git a/src/mesa/drivers/dri/i965/brw_primitive_restart.c b/src/mesa/drivers/dri/i965/brw_primitive_restart.c
index 38b5243..8c7219d 100644
--- a/src/mesa/drivers/dri/i965/brw_primitive_restart.c
+++ b/src/mesa/drivers/dri/i965/brw_primitive_restart.c
@@ -52,13 +52,13 @@ can_cut_index_handle_restart_index(struct gl_context *ctx,
 
    switch (ib->type) {
    case GL_UNSIGNED_BYTE:
-      cut_index_will_work = (ctx->Array.RestartIndex & 0xff) == 0xff;
+      cut_index_will_work = (ctx->Array._RestartIndex & 0xff) == 0xff;
       break;
    case GL_UNSIGNED_SHORT:
-      cut_index_will_work = (ctx->Array.RestartIndex & 0xffff) == 0xffff;
+      cut_index_will_work = (ctx->Array._RestartIndex & 0xffff) == 0xffff;
       break;
    case GL_UNSIGNED_INT:
-      cut_index_will_work = ctx->Array.RestartIndex == 0xffffffff;
+      cut_index_will_work = ctx->Array._RestartIndex == 0xffffffff;
       break;
    default:
       cut_index_will_work = false;
@@ -157,7 +157,7 @@ brw_handle_primitive_restart(struct gl_context *ctx,
    /* If PrimitiveRestart is not enabled, then we aren't concerned about
     * handling this draw.
     */
-   if (!(ctx->Array.PrimitiveRestart)) {
+   if (!(ctx->Array._PrimitiveRestart)) {
       return GL_FALSE;
    }
 
diff --git a/src/mesa/main/api_arrayelt.c b/src/mesa/main/api_arrayelt.c
index 0fa2429..ea33614 100644
--- a/src/mesa/main/api_arrayelt.c
+++ b/src/mesa/main/api_arrayelt.c
@@ -1636,7 +1636,7 @@ void GLAPIENTRY _ae_ArrayElement( GLint elt )
    /* If PrimitiveRestart is enabled and the index is the RestartIndex
     * then we call PrimitiveRestartNV and return.
     */
-   if (ctx->Array.PrimitiveRestart && (elt == ctx->Array.RestartIndex)) {
+   if (ctx->Array._PrimitiveRestart && (elt == ctx->Array._RestartIndex)) {
       CALL_PrimitiveRestartNV((struct _glapi_table *)disp, ());
       return;
    }
diff --git a/src/mesa/main/attrib.c b/src/mesa/main/attrib.c
index a19d610..d6f298d 100644
--- a/src/mesa/main/attrib.c
+++ b/src/mesa/main/attrib.c
@@ -1377,7 +1377,10 @@ copy_array_attrib(struct gl_context *ctx,
    dest->LockFirst = src->LockFirst;
    dest->LockCount = src->LockCount;
    dest->PrimitiveRestart = src->PrimitiveRestart;
+   dest->PrimitiveRestartFixedIndex = src->PrimitiveRestartFixedIndex;
+   dest->_PrimitiveRestart = src->_PrimitiveRestart;
    dest->RestartIndex = src->RestartIndex;
+   dest->_RestartIndex = src->_RestartIndex;
    /* skip NewState */
    /* skip RebindArrays */
 
diff --git a/src/mesa/main/enable.c b/src/mesa/main/enable.c
index b48794f..7325729 100644
--- a/src/mesa/main/enable.c
+++ b/src/mesa/main/enable.c
@@ -48,6 +48,20 @@
    }
 
 
+static void
+update_derived_primitive_restart_state(struct gl_context *ctx)
+{
+   /* Update derived primitive restart state.
+    */
+   if (ctx->Array.PrimitiveRestart)
+      ctx->Array._RestartIndex = ctx->Array.RestartIndex;
+   else
+      ctx->Array._RestartIndex = ~0;
+
+   ctx->Array._PrimitiveRestart = ctx->Array.PrimitiveRestart
+      || ctx->Array.PrimitiveRestartFixedIndex;
+}
+
 /**
  * Helper to enable/disable client-side state.
  */
@@ -119,6 +133,8 @@ client_state(struct gl_context *ctx, GLenum cap, GLboolean state)
 
    *var = state;
 
+   update_derived_primitive_restart_state(ctx);
+
    if (state)
       arrayObj->_Enabled |= flag;
    else
@@ -967,6 +983,17 @@ _mesa_set_enable(struct gl_context *ctx, GLenum cap, GLboolean state)
          if (ctx->Array.PrimitiveRestart != state) {
             FLUSH_VERTICES(ctx, _NEW_TRANSFORM);
             ctx->Array.PrimitiveRestart = state;
+            update_derived_primitive_restart_state(ctx);
+         }
+         break;
+
+      case GL_PRIMITIVE_RESTART_FIXED_INDEX:
+	 if (!_mesa_is_gles3(ctx) && !ctx->Extensions.ARB_ES3_compatibility)
+            goto invalid_enum_error;
+         if (ctx->Array.PrimitiveRestartFixedIndex != state) {
+            FLUSH_VERTICES(ctx, _NEW_TRANSFORM);
+            ctx->Array.PrimitiveRestartFixedIndex = state;
+            update_derived_primitive_restart_state(ctx);
          }
          break;
 
@@ -1542,6 +1569,12 @@ _mesa_IsEnabled( GLenum cap )
          }
          return ctx->Array.PrimitiveRestart;
 
+      case GL_PRIMITIVE_RESTART_FIXED_INDEX:
+	 if (!_mesa_is_gles3(ctx) && !ctx->Extensions.ARB_ES3_compatibility) {
+            goto invalid_enum_error;
+         }
+         return ctx->Array.PrimitiveRestartFixedIndex;
+
       /* GL3.0 - GL_framebuffer_sRGB */
       case GL_FRAMEBUFFER_SRGB_EXT:
          if (!_mesa_is_desktop_gl(ctx))
diff --git a/src/mesa/main/mtypes.h b/src/mesa/main/mtypes.h
index 318dcb5..f44ec49 100644
--- a/src/mesa/main/mtypes.h
+++ b/src/mesa/main/mtypes.h
@@ -1634,9 +1634,20 @@ struct gl_array_attrib
    GLuint LockFirst;            /**< GL_EXT_compiled_vertex_array */
    GLuint LockCount;            /**< GL_EXT_compiled_vertex_array */
 
-   /** GL 3.1 (slightly different from GL_NV_primitive_restart) */
+   /**
+    * \name Primitive restart controls
+    *
+    * Primitive restart is enabled if either \c PrimitiveRestart or
+    * \c PrimitiveRestart is set.  If \c PrimitiveRestart is set, then
+    * \c RestartIndex is used as the cut vertex.  Otherwise ~0 is used.
+    */
+   /*@{*/
    GLboolean PrimitiveRestart;
+   GLboolean PrimitiveRestartFixedIndex;
+   GLboolean _PrimitiveRestart;
    GLuint RestartIndex;
+   GLuint _RestartIndex;
+   /*@}*/
 
    /* GL_ARB_vertex_buffer_object */
    struct gl_buffer_object *ArrayBufferObj;
diff --git a/src/mesa/main/varray.c b/src/mesa/main/varray.c
index 5e4d6c3..e453b3b 100644
--- a/src/mesa/main/varray.c
+++ b/src/mesa/main/varray.c
@@ -1113,9 +1113,10 @@ _mesa_PrimitiveRestartIndex(GLuint index)
 
    ASSERT_OUTSIDE_BEGIN_END(ctx);
 
-   if (ctx->Array.RestartIndex != index) {
+   ctx->Array.RestartIndex = index;
+   if (ctx->Array.PrimitiveRestart && ctx->Array._RestartIndex != index) {
       FLUSH_VERTICES(ctx, _NEW_TRANSFORM);
-      ctx->Array.RestartIndex = index;
+      ctx->Array._RestartIndex = index;
    }
 }
 
diff --git a/src/mesa/state_tracker/st_draw.c b/src/mesa/state_tracker/st_draw.c
index 4800e1c..7de2bb9 100644
--- a/src/mesa/state_tracker/st_draw.c
+++ b/src/mesa/state_tracker/st_draw.c
@@ -230,8 +230,8 @@ st_draw_vbo(struct gl_context *ctx,
       /* The VBO module handles restart for the non-indexed GLDrawArrays
        * so we only set these fields for indexed drawing:
        */
-      info.primitive_restart = ctx->Array.PrimitiveRestart;
-      info.restart_index = ctx->Array.RestartIndex;
+      info.primitive_restart = ctx->Array._PrimitiveRestart;
+      info.restart_index = ctx->Array._RestartIndex;
    }
    else {
       /* Transform feedback drawing is always non-indexed. */
diff --git a/src/mesa/vbo/vbo_exec_array.c b/src/mesa/vbo/vbo_exec_array.c
index 4b2c529..7e61f7b 100644
--- a/src/mesa/vbo/vbo_exec_array.c
+++ b/src/mesa/vbo/vbo_exec_array.c
@@ -90,8 +90,8 @@ vbo_get_minmax_index(struct gl_context *ctx,
 		     GLuint *min_index, GLuint *max_index,
 		     const GLuint count)
 {
-   const GLboolean restart = ctx->Array.PrimitiveRestart;
-   const GLuint restartIndex = ctx->Array.RestartIndex;
+   const GLboolean restart = ctx->Array._PrimitiveRestart;
+   const GLuint restartIndex = ctx->Array._RestartIndex;
    const int index_size = vbo_sizeof_ib_type(ib->type);
    const char *indices;
    GLuint i;
@@ -536,7 +536,7 @@ vbo_handle_primitive_restart(struct gl_context *ctx,
 
    if ((ib != NULL) &&
        ctx->Const.PrimitiveRestartInSoftware &&
-       ctx->Array.PrimitiveRestart) {
+       ctx->Array._PrimitiveRestart) {
       /* Handle primitive restart in software */
       vbo_sw_primitive_restart(ctx, prim, nr_prims, ib);
    } else {
@@ -572,10 +572,10 @@ vbo_draw_arrays(struct gl_context *ctx, GLenum mode, GLint start,
    prim[0].base_instance = baseInstance;
 
    /* Implement the primitive restart index */
-   if (ctx->Array.PrimitiveRestart && ctx->Array.RestartIndex < count) {
+   if (ctx->Array._PrimitiveRestart && ctx->Array._RestartIndex < count) {
       GLuint primCount = 0;
 
-      if (ctx->Array.RestartIndex == start) {
+      if (ctx->Array._RestartIndex == start) {
          /* special case: RestartIndex at beginning */
          if (count > 1) {
             prim[0].start = start + 1;
@@ -583,7 +583,7 @@ vbo_draw_arrays(struct gl_context *ctx, GLenum mode, GLint start,
             primCount = 1;
          }
       }
-      else if (ctx->Array.RestartIndex == start + count - 1) {
+      else if (ctx->Array._RestartIndex == start + count - 1) {
          /* special case: RestartIndex at end */
          if (count > 1) {
             prim[0].start = start;
@@ -594,10 +594,10 @@ vbo_draw_arrays(struct gl_context *ctx, GLenum mode, GLint start,
       else {
          /* general case: RestartIndex in middle, split into two prims */
          prim[0].start = start;
-         prim[0].count = ctx->Array.RestartIndex - start;
+         prim[0].count = ctx->Array._RestartIndex - start;
 
          prim[1] = prim[0];
-         prim[1].start = ctx->Array.RestartIndex + 1;
+         prim[1].start = ctx->Array._RestartIndex + 1;
          prim[1].count = count - prim[1].start;
 
          primCount = 2;
diff --git a/src/mesa/vbo/vbo_primitive_restart.c b/src/mesa/vbo/vbo_primitive_restart.c
index 6f9d61c..a6a0149 100644
--- a/src/mesa/vbo/vbo_primitive_restart.c
+++ b/src/mesa/vbo/vbo_primitive_restart.c
@@ -171,7 +171,7 @@ vbo_sw_primitive_restart(struct gl_context *ctx,
    GLuint sub_prim_num;
    GLuint end_index;
    GLuint sub_end_index;
-   GLuint restart_index = ctx->Array.RestartIndex;
+   GLuint restart_index = ctx->Array._RestartIndex;
    struct _mesa_prim temp_prim;
    struct vbo_context *vbo = vbo_context(ctx);
    vbo_draw_func draw_prims_func = vbo->draw_prims;




More information about the mesa-commit mailing list