Mesa (main): mesa: refine name stack code to prepare for hw select

GitLab Mirror gitlab-mirror at kemper.freedesktop.org
Mon Jun 6 19:05:07 UTC 2022


Module: Mesa
Branch: main
Commit: 429c7fbaa1d87611a67339fa8b26e869e170c1a9
URL:    http://cgit.freedesktop.org/mesa/mesa/commit/?id=429c7fbaa1d87611a67339fa8b26e869e170c1a9

Author: Qiang Yu <yuq825 at gmail.com>
Date:   Wed Mar  9 14:33:22 2022 +0800

mesa: refine name stack code to prepare for hw select

No functional change, just pack existing software based implementation into
the HardwareAcceleratedSelect switch, will add hardware implementation in
next commit.

ctx->Select.NameStackDepth is sure to be <=MAX_NAME_STACK_DEPTH, so removed
the overflow check in _mesa_LoadName.

Reviewed-by: Marek Olšák <marek.olsak at amd.com>
Reviewed-by: Pierre-Eric Pelloux-Prayer <pierre-eric.pelloux-prayer at amd.com>
Sgined-off-by: Qiang Yu <yuq825 at gmail.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/15765>

---

 src/mesa/main/feedback.c | 158 +++++++++++++++++++++--------------------------
 1 file changed, 70 insertions(+), 88 deletions(-)

diff --git a/src/mesa/main/feedback.c b/src/mesa/main/feedback.c
index 8daa85e4e4f..27880188d5f 100644
--- a/src/mesa/main/feedback.c
+++ b/src/mesa/main/feedback.c
@@ -221,68 +221,66 @@ _mesa_update_hitflag(struct gl_context *ctx, GLfloat z)
    }
 }
 
-
-/**
- * Write the hit record.
- *
- * \param ctx GL context.
- *
- * Write the hit record, i.e., the number of names in the stack, the minimum and
- * maximum depth values and the number of names in the name stack at the time
- * of the event. Resets the hit flag. 
- *
- * \sa gl_selection.
- */
 static void
-write_hit_record(struct gl_context *ctx)
+update_hit_record(struct gl_context *ctx)
 {
-   GLuint i;
-   GLuint zmin, zmax, zscale = (~0u);
+   struct gl_selection *s = &ctx->Select;
 
-   /* HitMinZ and HitMaxZ are in [0,1].  Multiply these values by */
-   /* 2^32-1 and round to nearest unsigned integer. */
+   if (ctx->Const.HardwareAcceleratedSelect) {
 
-   assert( ctx != NULL ); /* this line magically fixes a SunOS 5.x/gcc bug */
-   zmin = (GLuint) ((GLfloat) zscale * ctx->Select.HitMinZ);
-   zmax = (GLuint) ((GLfloat) zscale * ctx->Select.HitMaxZ);
+   } else {
+      if (!s->HitFlag)
+         return;
 
-   write_record( ctx, ctx->Select.NameStackDepth );
-   write_record( ctx, zmin );
-   write_record( ctx, zmax );
-   for (i = 0; i < ctx->Select.NameStackDepth; i++) {
-      write_record( ctx, ctx->Select.NameStack[i] );
-   }
+      /* HitMinZ and HitMaxZ are in [0,1].  Multiply these values by */
+      /* 2^32-1 and round to nearest unsigned integer. */
+      GLuint zscale = (~0u);
+      GLuint zmin = (GLuint) ((GLfloat) zscale * s->HitMinZ);
+      GLuint zmax = (GLuint) ((GLfloat) zscale * s->HitMaxZ);
 
-   ctx->Select.Hits++;
-   ctx->Select.HitFlag = GL_FALSE;
-   ctx->Select.HitMinZ = 1.0;
-   ctx->Select.HitMaxZ = -1.0;
+      write_record(ctx, s->NameStackDepth);
+      write_record(ctx, zmin);
+      write_record(ctx, zmax);
+      for (int i = 0; i < s->NameStackDepth; i++)
+         write_record(ctx, s->NameStack[i]);
+
+      s->HitFlag = GL_FALSE;
+      s->HitMinZ = 1.0;
+      s->HitMaxZ = -1.0;
+
+      s->Hits++;
+   }
 }
 
+static void
+reset_name_stack_to_empty(struct gl_context *ctx)
+{
+   struct gl_selection *s = &ctx->Select;
+
+   s->NameStackDepth = 0;
+   s->HitFlag = GL_FALSE;
+   s->HitMinZ = 1.0;
+   s->HitMaxZ = 0.0;
+}
 
 /**
  * Initialize the name stack.
- *
- * Verifies we are in select mode and resets the name stack depth and resets
- * the hit record data in gl_selection. Marks new render mode in
- * __struct gl_contextRec::NewState.
  */
 void GLAPIENTRY
 _mesa_InitNames( void )
 {
    GET_CURRENT_CONTEXT(ctx);
+
+   /* Calls to glInitNames while the render mode is not GL_SELECT are ignored. */
+   if (ctx->RenderMode != GL_SELECT)
+      return;
+
    FLUSH_VERTICES(ctx, 0, 0);
 
-   /* Record the hit before the HitFlag is wiped out again. */
-   if (ctx->RenderMode == GL_SELECT) {
-      if (ctx->Select.HitFlag) {
-         write_hit_record( ctx );
-      }
-   }
-   ctx->Select.NameStackDepth = 0;
-   ctx->Select.HitFlag = GL_FALSE;
-   ctx->Select.HitMinZ = 1.0;
-   ctx->Select.HitMaxZ = 0.0;
+   update_hit_record(ctx);
+
+   reset_name_stack_to_empty(ctx);
+
    ctx->NewState |= _NEW_RENDERMODE;
 }
 
@@ -291,12 +289,6 @@ _mesa_InitNames( void )
  * Load the top-most name of the name stack.
  *
  * \param name name.
- *
- * Verifies we are in selection mode and that the name stack is not empty.
- * Flushes vertices. If there is a hit flag writes it (via write_hit_record()),
- * and replace the top-most name in the stack.
- *
- * sa __struct gl_contextRec::Select.
  */
 void GLAPIENTRY
 _mesa_LoadName( GLuint name )
@@ -311,17 +303,13 @@ _mesa_LoadName( GLuint name )
       return;
    }
 
-   FLUSH_VERTICES(ctx, _NEW_RENDERMODE, 0);
-
-   if (ctx->Select.HitFlag) {
-      write_hit_record( ctx );
-   }
-   if (ctx->Select.NameStackDepth < MAX_NAME_STACK_DEPTH) {
-      ctx->Select.NameStack[ctx->Select.NameStackDepth-1] = name;
-   }
-   else {
-      ctx->Select.NameStack[MAX_NAME_STACK_DEPTH-1] = name;
+   if (!ctx->Const.HardwareAcceleratedSelect) {
+      FLUSH_VERTICES(ctx, 0, 0);
+      update_hit_record(ctx);
    }
+
+   ctx->Select.NameStack[ctx->Select.NameStackDepth-1] = name;
+   ctx->NewState |= _NEW_RENDERMODE;
 }
 
 
@@ -329,12 +317,6 @@ _mesa_LoadName( GLuint name )
  * Push a name into the name stack.
  *
  * \param name name.
- *
- * Verifies we are in selection mode and that the name stack is not full.
- * Flushes vertices. If there is a hit flag writes it (via write_hit_record()),
- * and adds the name to the top of the name stack.
- *
- * sa __struct gl_contextRec::Select.
  */
 void GLAPIENTRY
 _mesa_PushName( GLuint name )
@@ -345,26 +327,23 @@ _mesa_PushName( GLuint name )
       return;
    }
 
-   FLUSH_VERTICES(ctx, _NEW_RENDERMODE, 0);
-   if (ctx->Select.HitFlag) {
-      write_hit_record( ctx );
-   }
    if (ctx->Select.NameStackDepth >= MAX_NAME_STACK_DEPTH) {
       _mesa_error( ctx, GL_STACK_OVERFLOW, "glPushName" );
+      return;
+   }
+
+   if (!ctx->Const.HardwareAcceleratedSelect) {
+      FLUSH_VERTICES(ctx, 0, 0);
+      update_hit_record(ctx);
    }
-   else
-      ctx->Select.NameStack[ctx->Select.NameStackDepth++] = name;
+
+   ctx->Select.NameStack[ctx->Select.NameStackDepth++] = name;
+   ctx->NewState |= _NEW_RENDERMODE;
 }
 
 
 /**
  * Pop a name into the name stack.
- *
- * Verifies we are in selection mode and that the name stack is not empty.
- * Flushes vertices. If there is a hit flag writes it (via write_hit_record()),
- * and removes top-most name in the name stack.
- *
- * sa __struct gl_contextRec::Select.
  */
 void GLAPIENTRY
 _mesa_PopName( void )
@@ -375,15 +354,18 @@ _mesa_PopName( void )
       return;
    }
 
-   FLUSH_VERTICES(ctx, _NEW_RENDERMODE, 0);
-   if (ctx->Select.HitFlag) {
-      write_hit_record( ctx );
-   }
    if (ctx->Select.NameStackDepth == 0) {
       _mesa_error( ctx, GL_STACK_UNDERFLOW, "glPopName" );
+      return;
    }
-   else
-      ctx->Select.NameStackDepth--;
+
+   if (!ctx->Const.HardwareAcceleratedSelect) {
+      FLUSH_VERTICES(ctx, 0, 0);
+      update_hit_record(ctx);
+   }
+
+   ctx->Select.NameStackDepth--;
+   ctx->NewState |= _NEW_RENDERMODE;
 }
 
 /*@}*/
@@ -426,9 +408,8 @@ _mesa_RenderMode( GLenum mode )
 	 result = 0;
 	 break;
       case GL_SELECT:
-	 if (ctx->Select.HitFlag) {
-	    write_hit_record( ctx );
-	 }
+	 update_hit_record(ctx);
+
 	 if (ctx->Select.BufferCount > ctx->Select.BufferSize) {
 	    /* overflow */
 #ifndef NDEBUG
@@ -441,7 +422,8 @@ _mesa_RenderMode( GLenum mode )
 	 }
 	 ctx->Select.BufferCount = 0;
 	 ctx->Select.Hits = 0;
-	 ctx->Select.NameStackDepth = 0;
+	 /* name stack should be in empty state after exiting GL_SELECT mode */
+	 reset_name_stack_to_empty(ctx);
 	 break;
       case GL_FEEDBACK:
 	 if (ctx->Feedback.Count > ctx->Feedback.BufferSize) {



More information about the mesa-commit mailing list