[Mesa-dev] [PATCH v2 1/2] mesa: Implement ARB_texture_filter_minmax

Scott D Phillips scott.d.phillips at intel.com
Wed Nov 22 00:47:00 UTC 2017


This extension provides a new texture and sampler parameter
(TEXTURE_REDUCTION_MODE_ARB) which allows applications to produce
a filtered texel value by computing a component-wise minimum (MIN)
or maximum (MAX) of the texels that would normally be averaged.

v2: - Remove extension from compat contexts (Ian Romanick)
    - Add missing extension checks & early return (Emil Velikov)
---
 src/mesa/main/attrib.c           |  4 ++++
 src/mesa/main/extensions_table.h |  1 +
 src/mesa/main/formatquery.c      | 18 ++++++++++++++++
 src/mesa/main/mtypes.h           |  2 ++
 src/mesa/main/samplerobj.c       | 45 ++++++++++++++++++++++++++++++++++++++++
 src/mesa/main/texobj.c           |  2 ++
 src/mesa/main/texobj.h           |  2 +-
 src/mesa/main/texparam.c         | 34 ++++++++++++++++++++++++++++++
 8 files changed, 107 insertions(+), 1 deletion(-)

diff --git a/src/mesa/main/attrib.c b/src/mesa/main/attrib.c
index 43b5856901..a5c9a32513 100644
--- a/src/mesa/main/attrib.c
+++ b/src/mesa/main/attrib.c
@@ -884,6 +884,10 @@ pop_texture_group(struct gl_context *ctx, struct texture_state *texstate)
             _mesa_TexParameterf(target, GL_TEXTURE_MAX_ANISOTROPY_EXT,
                                 samp->MaxAnisotropy);
          }
+         if (ctx->Extensions.ARB_texture_filter_minmax) {
+            _mesa_TexParameteri(target, GL_TEXTURE_REDUCTION_MODE_ARB,
+                                samp->ReductionMode);
+         }
          if (ctx->Extensions.ARB_shadow) {
             _mesa_TexParameteri(target, GL_TEXTURE_COMPARE_MODE,
                                 samp->CompareMode);
diff --git a/src/mesa/main/extensions_table.h b/src/mesa/main/extensions_table.h
index 5b66e7d30d..3a7c3cf1d4 100644
--- a/src/mesa/main/extensions_table.h
+++ b/src/mesa/main/extensions_table.h
@@ -146,6 +146,7 @@ EXT(ARB_texture_env_combine                 , ARB_texture_env_combine
 EXT(ARB_texture_env_crossbar                , ARB_texture_env_crossbar               , GLL,  x ,  x ,  x , 2001)
 EXT(ARB_texture_env_dot3                    , ARB_texture_env_dot3                   , GLL,  x ,  x ,  x , 2001)
 EXT(ARB_texture_filter_anisotropic          , ARB_texture_filter_anisotropic         , GLL, GLC,  x ,  x , 2017)
+EXT(ARB_texture_filter_minmax               , ARB_texture_filter_minmax              ,  x , GLC,  x ,  x , 2017)
 EXT(ARB_texture_float                       , ARB_texture_float                      , GLL, GLC,  x ,  x , 2004)
 EXT(ARB_texture_gather                      , ARB_texture_gather                     , GLL, GLC,  x ,  x , 2009)
 EXT(ARB_texture_mirror_clamp_to_edge        , ARB_texture_mirror_clamp_to_edge       , GLL, GLC,  x ,  x , 2013)
diff --git a/src/mesa/main/formatquery.c b/src/mesa/main/formatquery.c
index 61f798c88f..52c7c25d8c 100644
--- a/src/mesa/main/formatquery.c
+++ b/src/mesa/main/formatquery.c
@@ -232,6 +232,15 @@ _legal_parameters(struct gl_context *ctx, GLenum target, GLenum internalformat,
       }
       break;
 
+   case GL_TEXTURE_REDUCTION_MODE_ARB:
+      if (!query2 || !_mesa_has_ARB_texture_filter_minmax(ctx)) {
+         _mesa_error(ctx, GL_INVALID_ENUM,
+                     "glGetInternalformativ(pname=%s)",
+                     _mesa_enum_to_string(pname));
+         return false;
+      }
+      break;
+
    default:
       _mesa_error(ctx, GL_INVALID_ENUM,
                   "glGetInternalformativ(pname=%s)",
@@ -375,6 +384,7 @@ _set_default_response(GLenum pname, GLint buffer[16])
    case GL_STENCIL_RENDERABLE:
    case GL_MIPMAP:
    case GL_TEXTURE_COMPRESSED:
+   case GL_TEXTURE_REDUCTION_MODE_ARB:
       buffer[0] = GL_FALSE;
       break;
 
@@ -1542,6 +1552,14 @@ _mesa_GetInternalformativ(GLenum target, GLenum internalformat, GLenum pname,
                                       buffer);
       break;
 
+   case GL_TEXTURE_REDUCTION_MODE_ARB:
+      if (!_mesa_has_ARB_texture_filter_minmax(ctx))
+         goto end;
+
+      ctx->Driver.QueryInternalFormat(ctx, target, internalformat, pname,
+                                      buffer);
+      break;
+
    default:
       unreachable("bad param");
    }
diff --git a/src/mesa/main/mtypes.h b/src/mesa/main/mtypes.h
index 4682e02fc8..83cf56c0a1 100644
--- a/src/mesa/main/mtypes.h
+++ b/src/mesa/main/mtypes.h
@@ -989,6 +989,7 @@ struct gl_sampler_object
    GLenum CompareFunc;		/**< GL_ARB_shadow */
    GLenum sRGBDecode;           /**< GL_DECODE_EXT or GL_SKIP_DECODE_EXT */
    GLboolean CubeMapSeamless;   /**< GL_AMD_seamless_cubemap_per_texture */
+   GLenum ReductionMode;        /**< GL_ARB_texture_filter_minmax */
 
    /** GL_ARB_bindless_texture */
    bool HandleAllocated;
@@ -4107,6 +4108,7 @@ struct gl_extensions
    GLboolean ARB_texture_env_crossbar;
    GLboolean ARB_texture_env_dot3;
    GLboolean ARB_texture_filter_anisotropic;
+   GLboolean ARB_texture_filter_minmax;
    GLboolean ARB_texture_float;
    GLboolean ARB_texture_gather;
    GLboolean ARB_texture_mirror_clamp_to_edge;
diff --git a/src/mesa/main/samplerobj.c b/src/mesa/main/samplerobj.c
index 5ebf9e24f9..ce8819af38 100644
--- a/src/mesa/main/samplerobj.c
+++ b/src/mesa/main/samplerobj.c
@@ -135,6 +135,7 @@ _mesa_init_sampler_object(struct gl_sampler_object *sampObj, GLuint name)
    sampObj->sRGBDecode = GL_DECODE_EXT;
    sampObj->CubeMapSeamless = GL_FALSE;
    sampObj->HandleAllocated = GL_FALSE;
+   sampObj->ReductionMode = GL_WEIGHTED_AVERAGE_ARB;
 
    /* GL_ARB_bindless_texture */
    _mesa_init_sampler_handles(sampObj);
@@ -852,6 +853,27 @@ set_sampler_srgb_decode(struct gl_context *ctx,
    return GL_TRUE;
 }
 
+static GLuint
+set_sampler_reduction_mode(struct gl_context *ctx,
+                         struct gl_sampler_object *samp, GLint param)
+{
+   if (!ctx->Extensions.ARB_texture_filter_minmax)
+      return INVALID_PARAM;
+
+   if (samp->ReductionMode == param)
+      return GL_FALSE;
+
+   if (param != GL_MIN &&
+       param != GL_MAX &&
+       param != GL_WEIGHTED_AVERAGE_ARB) {
+      return INVALID_PARAM;
+   }
+
+   flush(ctx);
+   samp->ReductionMode = param;
+   return GL_TRUE;
+}
+
 static struct gl_sampler_object *
 sampler_parameter_error_check(struct gl_context *ctx, GLuint sampler,
                               bool get, const char *name)
@@ -937,6 +959,9 @@ _mesa_SamplerParameteri(GLuint sampler, GLenum pname, GLint param)
    case GL_TEXTURE_SRGB_DECODE_EXT:
       res = set_sampler_srgb_decode(ctx, sampObj, param);
       break;
+   case GL_TEXTURE_REDUCTION_MODE_ARB:
+      res = set_sampler_reduction_mode(ctx, sampObj, param);
+      break;
    case GL_TEXTURE_BORDER_COLOR:
       /* fall-through */
    default:
@@ -1464,6 +1489,11 @@ _mesa_GetSamplerParameteriv(GLuint sampler, GLenum pname, GLint *params)
          goto invalid_pname;
       *params = (GLenum) sampObj->sRGBDecode;
       break;
+   case GL_TEXTURE_REDUCTION_MODE_ARB:
+      if (!ctx->Extensions.ARB_texture_filter_minmax)
+         goto invalid_pname;
+      *params = sampObj->ReductionMode;
+      break;
    default:
       goto invalid_pname;
    }
@@ -1536,6 +1566,11 @@ _mesa_GetSamplerParameterfv(GLuint sampler, GLenum pname, GLfloat *params)
          goto invalid_pname;
       *params = (GLfloat) sampObj->sRGBDecode;
       break;
+   case GL_TEXTURE_REDUCTION_MODE_ARB:
+      if (!ctx->Extensions.ARB_texture_filter_minmax)
+         goto invalid_pname;
+      *params = (GLfloat) sampObj->ReductionMode;
+      break;
    default:
       goto invalid_pname;
    }
@@ -1608,6 +1643,11 @@ _mesa_GetSamplerParameterIiv(GLuint sampler, GLenum pname, GLint *params)
          goto invalid_pname;
       *params = (GLenum) sampObj->sRGBDecode;
       break;
+   case GL_TEXTURE_REDUCTION_MODE_ARB:
+      if (!ctx->Extensions.ARB_texture_filter_minmax)
+         goto invalid_pname;
+      *params = sampObj->ReductionMode;
+      break;
    default:
       goto invalid_pname;
    }
@@ -1680,6 +1720,11 @@ _mesa_GetSamplerParameterIuiv(GLuint sampler, GLenum pname, GLuint *params)
          goto invalid_pname;
       *params = (GLenum) sampObj->sRGBDecode;
       break;
+   case GL_TEXTURE_REDUCTION_MODE_ARB:
+      if (!ctx->Extensions.ARB_texture_filter_minmax)
+         goto invalid_pname;
+      *params = sampObj->ReductionMode;
+      break;
    default:
       goto invalid_pname;
    }
diff --git a/src/mesa/main/texobj.c b/src/mesa/main/texobj.c
index 02c4767788..a81692d22f 100644
--- a/src/mesa/main/texobj.c
+++ b/src/mesa/main/texobj.c
@@ -325,6 +325,7 @@ _mesa_initialize_texture_object( struct gl_context *ctx,
    obj->BufferObjectFormat = GL_R8;
    obj->_BufferObjectFormat = MESA_FORMAT_R_UNORM8;
    obj->ImageFormatCompatibilityType = GL_IMAGE_FORMAT_COMPATIBILITY_BY_SIZE;
+   obj->Sampler.ReductionMode = GL_WEIGHTED_AVERAGE_ARB;
 
    /* GL_ARB_bindless_texture */
    _mesa_init_texture_handles(obj);
@@ -465,6 +466,7 @@ _mesa_copy_texture_object( struct gl_texture_object *dest,
    dest->_Swizzle = src->_Swizzle;
    dest->_IsHalfFloat = src->_IsHalfFloat;
    dest->_IsFloat = src->_IsFloat;
+   dest->Sampler.ReductionMode = src->Sampler.ReductionMode;
 
    dest->RequiredTextureImageUnits = src->RequiredTextureImageUnits;
 }
diff --git a/src/mesa/main/texobj.h b/src/mesa/main/texobj.h
index e67ce3ff9d..306f4a7740 100644
--- a/src/mesa/main/texobj.h
+++ b/src/mesa/main/texobj.h
@@ -125,7 +125,7 @@ _mesa_is_texture_complete(const struct gl_texture_object *texObj,
     * be forbidden, however it is allowed per GL 4.5 rules, allow it
     * even without GL 4.5 since it was a spec mistake.
     */
-   if ((texObj->_IsIntegerFormat ||
+   if (((texObj->_IsIntegerFormat && sampler->ReductionMode == GL_WEIGHTED_AVERAGE_ARB) ||
         (texObj->StencilSampling &&
          texObj->Image[0][texObj->BaseLevel]->_BaseFormat == GL_DEPTH_STENCIL)) &&
        (sampler->MagFilter != GL_NEAREST ||
diff --git a/src/mesa/main/texparam.c b/src/mesa/main/texparam.c
index 4a0f61eda8..2729dba4a4 100644
--- a/src/mesa/main/texparam.c
+++ b/src/mesa/main/texparam.c
@@ -630,6 +630,26 @@ set_tex_parameteri(struct gl_context *ctx,
       }
       goto invalid_pname;
 
+   case GL_TEXTURE_REDUCTION_MODE_ARB:
+      if (!ctx->Extensions.ARB_texture_filter_minmax)
+         goto invalid_pname;
+
+      if (!_mesa_target_allows_setting_sampler_parameters(texObj->Target))
+         goto invalid_enum;
+
+      if (texObj->Sampler.ReductionMode == params[0])
+         return GL_FALSE;
+
+      if (params[0] != GL_MIN &&
+          params[0] != GL_MAX &&
+          params[0] != GL_WEIGHTED_AVERAGE_ARB) {
+         goto invalid_pname;
+      }
+
+      flush(ctx);
+      texObj->Sampler.ReductionMode = params[0];
+      return GL_TRUE;
+
    default:
       goto invalid_pname;
    }
@@ -836,6 +856,7 @@ _mesa_texture_parameterf(struct gl_context *ctx,
    case GL_TEXTURE_SWIZZLE_G_EXT:
    case GL_TEXTURE_SWIZZLE_B_EXT:
    case GL_TEXTURE_SWIZZLE_A_EXT:
+   case GL_TEXTURE_REDUCTION_MODE_ARB:
       {
          GLint p[4];
          p[0] = (param > 0) ?
@@ -888,6 +909,7 @@ _mesa_texture_parameterfv(struct gl_context *ctx,
    case GL_DEPTH_STENCIL_TEXTURE_MODE:
    case GL_TEXTURE_SRGB_DECODE_EXT:
    case GL_TEXTURE_CUBE_MAP_SEAMLESS:
+   case GL_TEXTURE_REDUCTION_MODE_ARB:
       {
          /* convert float param to int */
          GLint p[4];
@@ -2040,6 +2062,12 @@ get_tex_parameterfv(struct gl_context *ctx,
          *params = ENUM_TO_FLOAT(obj->TextureTiling);
          break;
 
+      case GL_TEXTURE_REDUCTION_MODE_ARB:
+         if (!ctx->Extensions.ARB_texture_filter_minmax)
+            goto invalid_pname;
+         *params = (GLfloat) obj->Sampler.ReductionMode;
+         break;
+
       default:
          goto invalid_pname;
    }
@@ -2278,6 +2306,12 @@ get_tex_parameteriv(struct gl_context *ctx,
          *params = (GLint) obj->TextureTiling;
          break;
 
+      case GL_TEXTURE_REDUCTION_MODE_ARB:
+         if (!ctx->Extensions.ARB_texture_filter_minmax)
+            goto invalid_pname;
+         *params = (GLint) obj->Sampler.ReductionMode;
+         break;
+
       default:
          goto invalid_pname;
    }
-- 
2.14.3



More information about the mesa-dev mailing list