[Mesa-dev] [PATCH] i965: Make glGetTex to PBO path use blorp to handle swizzled formats

Jon Ashburn jon at lunarg.com
Wed Jun 25 11:05:22 PDT 2014


Existing texture read into PBO was using GPU Blit engine in which src and
dest formats must match.  With commit 61e264f4fcdba, internally stored texture
formats were no longer swizzled (BGRA instead of RGBA). This caused existing
accelerated paths to fallback to the SW slow path since the internal texture
format and the PBO format no longer matched.

Switch glGetTexImage to PBO case to use blorp instead of GPU BLIT engine and
handle formats that match but are swizzled using blorp.
---
 src/mesa/drivers/dri/i965/intel_tex_image.c | 52 ++++++++++++++++++++++++-----
 1 file changed, 43 insertions(+), 9 deletions(-)

diff --git a/src/mesa/drivers/dri/i965/intel_tex_image.c b/src/mesa/drivers/dri/i965/intel_tex_image.c
index de0546a..0e86396 100644
--- a/src/mesa/drivers/dri/i965/intel_tex_image.c
+++ b/src/mesa/drivers/dri/i965/intel_tex_image.c
@@ -24,6 +24,7 @@
 #include "intel_blit.h"
 #include "intel_fbo.h"
 #include "intel_image.h"
+#include "brw_blorp.h"
 
 #include "brw_context.h"
 
@@ -84,6 +85,32 @@ intel_miptree_create_for_teximage(struct brw_context *brw,
                                INTEL_MIPTREE_TILING_ANY);
 }
 
+static mesa_format
+format_swizzled_rgb(mesa_format format)
+{
+   switch (format) {
+   case MESA_FORMAT_B8G8R8X8_UNORM:
+      return MESA_FORMAT_R8G8B8X8_UNORM;
+   case MESA_FORMAT_B8G8R8A8_UNORM:
+      return MESA_FORMAT_R8G8B8A8_UNORM;
+   case MESA_FORMAT_R8G8B8X8_UNORM:
+      return MESA_FORMAT_B8G8R8X8_UNORM;
+   case MESA_FORMAT_R8G8B8A8_UNORM:
+      return  MESA_FORMAT_B8G8R8A8_UNORM;
+   case MESA_FORMAT_B8G8R8A8_SRGB:
+      return MESA_FORMAT_R8G8B8A8_SRGB;
+   case MESA_FORMAT_B8G8R8X8_SRGB:
+      return MESA_FORMAT_R8G8B8X8_SRGB;
+   case MESA_FORMAT_R8G8B8A8_SRGB:
+      return MESA_FORMAT_B8G8R8A8_SRGB;
+   case MESA_FORMAT_R8G8B8X8_SRGB:
+      return MESA_FORMAT_B8G8R8X8_SRGB;
+   default:
+      /* All other formats that aren't byte swizzable */
+      return MESA_FORMAT_NONE;
+   }
+}
+
 /* XXX: Do this for TexSubImage also:
  */
 static bool
@@ -427,15 +454,21 @@ blit_texture_to_pbo(struct gl_context *ctx,
    GLuint dst_offset;
    drm_intel_bo *dst_buffer;
    GLenum target = texImage->TexObject->Target;
+   bool rgb_swap;
+   mesa_format swizzle_format = format_swizzled_rgb(intelImage->mt->format);
 
    /* Check if we can use GPU blit to copy from the hardware texture
     * format to the user's format/type.
     * Note that GL's pixel transfer ops don't apply to glGetTexImage()
     */
 
-   if (!_mesa_format_matches_format_and_type(intelImage->mt->format, format,
-                                             type, false))
-   {
+   if (_mesa_format_matches_format_and_type(intelImage->mt->format, format,
+                                            type, false)) {
+      rgb_swap = false;
+   } else if (_mesa_format_matches_format_and_type(swizzle_format,
+                                                   format, type, false)) {
+      rgb_swap = true;
+   } else {
       perf_debug("%s: unsupported format, fallback to CPU mapping for PBO\n",
                  __FUNCTION__);
 
@@ -457,6 +490,7 @@ blit_texture_to_pbo(struct gl_context *ctx,
    if (target == GL_TEXTURE_1D_ARRAY ||
        target == GL_TEXTURE_2D_ARRAY ||
        target == GL_TEXTURE_CUBE_MAP_ARRAY ||
+       target == GL_TEXTURE_CUBE_MAP ||
        target == GL_TEXTURE_3D) {
       perf_debug("%s: no support for multiple slices, fallback to CPU mapping "
                  "for PBO\n", __FUNCTION__);
@@ -483,6 +517,7 @@ blit_texture_to_pbo(struct gl_context *ctx,
    struct intel_mipmap_tree *pbo_mt =
       intel_miptree_create_for_bo(brw,
                                   dst_buffer,
+                                  (rgb_swap) ? swizzle_format :
                                   intelImage->mt->format,
                                   dst_offset,
                                   texImage->Width, texImage->Height,
@@ -491,13 +526,12 @@ blit_texture_to_pbo(struct gl_context *ctx,
    if (!pbo_mt)
       return false;
 
-   if (!intel_miptree_blit(brw,
-                           intelImage->mt, texImage->Level, texImage->Face,
-                           0, 0, false,
+   brw_blorp_blit_miptrees(brw,
+                           intelImage->mt,  texImage->Level, texImage->Face,
                            pbo_mt, 0, 0,
-                           0, 0, dst_flip,
-                           texImage->Width, texImage->Height, GL_COPY))
-      return false;
+                           0, 0, texImage->Width, texImage->Height,
+                           0, 0, texImage->Width, texImage->Height,
+                           GL_NEAREST, dst_flip, false);
 
    intel_miptree_release(&pbo_mt);
 
-- 
1.8.1.2



More information about the mesa-dev mailing list