mesa: signal driver when buffer is bound to different texture format
authorGert Wollny <gert.wollny@collabora.com>
Wed, 6 Oct 2021 16:11:52 +0000 (18:11 +0200)
committerMarge Bot <eric+marge@anholt.net>
Thu, 7 Oct 2021 17:53:48 +0000 (17:53 +0000)
Gallium caches sampler states for TBOs. Now if a buffer is first
attached to a TBO specifying one format, and later attached by
specifying another format and this TBO is then used, that would lead
to an assertion failure in debug builds, or to invalid rendering in
release builds, because the TBO picks the original, wrong format for
the sampler view.

Resolve this by signalling the change to Gallium (and other drivers), so
that Gallium clears the sampler view cache.

Fixes: f0ecd36ef8e10c087738c92cf62bad3815366963
  st/mesa: add an entirely separate codepath for setting up buffer views

Signed-off-by: Gert Wollny <gert.wollny@collabora.com>
Reviewed-by: Marek Olšák <marek.olsak@amd.com>
Reviewed-by: Emma Anholt <emma@anholt.net>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/13230>

src/mesa/main/teximage.c

index 76a0586..4254f10 100644 (file)
@@ -6350,6 +6350,7 @@ texture_buffer_range(struct gl_context *ctx,
    GLintptr oldOffset = texObj->BufferOffset;
    GLsizeiptr oldSize = texObj->BufferSize;
    mesa_format format;
+   mesa_format old_format;
 
    /* NOTE: ARB_texture_buffer_object might not be supported in
     * the compatibility profile.
@@ -6387,6 +6388,7 @@ texture_buffer_range(struct gl_context *ctx,
    {
       _mesa_reference_buffer_object_shared(ctx, &texObj->BufferObject, bufObj);
       texObj->BufferObjectFormat = internalFormat;
+      old_format = texObj->_BufferObjectFormat;
       texObj->_BufferObjectFormat = format;
       texObj->BufferOffset = offset;
       texObj->BufferSize = size;
@@ -6394,11 +6396,15 @@ texture_buffer_range(struct gl_context *ctx,
    _mesa_unlock_texture(ctx, texObj);
 
    if (ctx->Driver.TexParameter) {
-      if (offset != oldOffset) {
-         ctx->Driver.TexParameter(ctx, texObj, GL_TEXTURE_BUFFER_OFFSET);
-      }
-      if (size != oldSize) {
-         ctx->Driver.TexParameter(ctx, texObj, GL_TEXTURE_BUFFER_SIZE);
+      if (old_format != format) {
+          ctx->Driver.TexParameter(ctx, texObj, GL_ALL_ATTRIB_BITS);
+      } else {
+          if (offset != oldOffset) {
+              ctx->Driver.TexParameter(ctx, texObj, GL_TEXTURE_BUFFER_OFFSET);
+          }
+          if (size != oldSize) {
+              ctx->Driver.TexParameter(ctx, texObj, GL_TEXTURE_BUFFER_SIZE);
+          }
       }
    }