[vlc-commits] gl: fix textures size/alignment for semi-planar chromas

Thomas Guillem git at videolan.org
Fri Apr 13 13:01:27 CEST 2018


vlc/vlc-3.0 | branch: master | Thomas Guillem <thomas at gllm.fr> | Fri Apr 13 11:51:11 2018 +0200| [22776daa29914cf56c346241f89682d5707ffef7] | committer: Hugo Beauzée-Luyssen

gl: fix textures size/alignment for semi-planar chromas

There were 2 errors that canceled each others:

 - The proper size for UV textures (GL_RG or GL_LUMINANCE_ALPHA) is w/2 x
   h/2 (and not w/2 x h/4).

 - Fix row length with GL_UNPACK_ROW_LENGTH or via an intermediate buffer.
   Don't use the pixel_pitch but the visible_pitch/texture_width ratio. Indeed,
   the pixel pitch for the UV plan of a semi-planar picture is 1 when the ratio
   is 2.

(cherry picked from commit 2599e2f7394972ec595b2f14d03bf0fb8f808c46)
Signed-off-by: Hugo Beauzée-Luyssen <hugo at beauzee.fr>

> http://git.videolan.org/gitweb.cgi/vlc/vlc-3.0.git/?a=commit;h=22776daa29914cf56c346241f89682d5707ffef7
---

 modules/video_output/opengl/converter_cvpx.c   |  2 --
 modules/video_output/opengl/converter_sw.c     | 28 ++++++++++++--------------
 modules/video_output/opengl/converter_vaapi.c  |  4 ----
 modules/video_output/opengl/fragment_shaders.c |  4 ++--
 4 files changed, 15 insertions(+), 23 deletions(-)

diff --git a/modules/video_output/opengl/converter_cvpx.c b/modules/video_output/opengl/converter_cvpx.c
index f0de830907..906533fd23 100644
--- a/modules/video_output/opengl/converter_cvpx.c
+++ b/modules/video_output/opengl/converter_cvpx.c
@@ -232,7 +232,6 @@ Open(vlc_object_t *obj)
             fragment_shader =
                 opengl_fragment_shader_init(tc, tex_target, VLC_CODEC_NV12,
                                             tc->fmt.space);
-            tc->texs[1].h = (vlc_rational_t) { 1, 2 };
             break;
         }
         case VLC_CODEC_CVPX_P010:
@@ -240,7 +239,6 @@ Open(vlc_object_t *obj)
             fragment_shader =
                 opengl_fragment_shader_init(tc, tex_target, VLC_CODEC_P010,
                                             tc->fmt.space);
-            tc->texs[1].h = (vlc_rational_t) { 1, 2 };
             break;
         }
         case VLC_CODEC_CVPX_I420:
diff --git a/modules/video_output/opengl/converter_sw.c b/modules/video_output/opengl/converter_sw.c
index e784d2503d..49b41f4826 100644
--- a/modules/video_output/opengl/converter_sw.c
+++ b/modules/video_output/opengl/converter_sw.c
@@ -230,8 +230,8 @@ tc_pbo_update(const opengl_tex_converter_t *tc, GLuint *textures,
         tc->vt->ActiveTexture(GL_TEXTURE0 + i);
         tc->vt->BindTexture(tc->tex_target, textures[i]);
 
-        tc->vt->PixelStorei(GL_UNPACK_ROW_LENGTH,
-                            pic->p[i].i_pitch / pic->p[i].i_pixel_pitch);
+        tc->vt->PixelStorei(GL_UNPACK_ROW_LENGTH, pic->p[i].i_pitch
+                                * tex_width[i] / pic->p[i].i_visible_pitch);
 
         tc->vt->TexSubImage2D(tc->tex_target, 0, 0, 0, tex_width[i], tex_height[i],
                               tc->texs[i].format, tc->texs[i].type, NULL);
@@ -333,8 +333,8 @@ tc_persistent_update(const opengl_tex_converter_t *tc, GLuint *textures,
         tc->vt->ActiveTexture(GL_TEXTURE0 + i);
         tc->vt->BindTexture(tc->tex_target, textures[i]);
 
-        tc->vt->PixelStorei(GL_UNPACK_ROW_LENGTH,
-                            pic->p[i].i_pitch / pic->p[i].i_pixel_pitch);
+        tc->vt->PixelStorei(GL_UNPACK_ROW_LENGTH, pic->p[i].i_pitch
+                                * tex_width[i] / pic->p[i].i_visible_pitch);
 
         tc->vt->TexSubImage2D(tc->tex_target, 0, 0, 0, tex_width[i], tex_height[i],
                               tc->texs[i].format, tc->texs[i].type, NULL);
@@ -441,7 +441,8 @@ tc_common_allocate_textures(const opengl_tex_converter_t *tc, GLuint *textures,
 static int
 upload_plane(const opengl_tex_converter_t *tc, unsigned tex_idx,
              GLsizei width, GLsizei height,
-             unsigned pitch, unsigned pixel_pitch, const void *pixels)
+             unsigned pitch, unsigned visible_pitch, unsigned pixel_pitch,
+             const void *pixels)
 {
     struct priv *priv = tc->priv;
     GLenum tex_format = tc->texs[tex_idx].format;
@@ -452,12 +453,9 @@ upload_plane(const opengl_tex_converter_t *tc, unsigned tex_idx,
 
     if (!priv->has_unpack_subimage)
     {
-#define ALIGN(x, y) (((x) + ((y) - 1)) & ~((y) - 1))
-        unsigned dst_width = width;
-        unsigned dst_pitch = ALIGN(dst_width * pixel_pitch, 4);
-        if (pitch != dst_pitch)
+        if (pitch != visible_pitch)
         {
-            size_t buf_size = dst_pitch * height * pixel_pitch;
+            size_t buf_size = visible_pitch * pixel_pitch * height;
             const uint8_t *source = pixels;
             uint8_t *destination;
             if (priv->texture_temp_buf_size < buf_size)
@@ -475,9 +473,9 @@ upload_plane(const opengl_tex_converter_t *tc, unsigned tex_idx,
 
             for (GLsizei h = 0; h < height ; h++)
             {
-                memcpy(destination, source, width * pixel_pitch);
+                memcpy(destination, source, visible_pitch);
                 source += pitch;
-                destination += dst_pitch;
+                destination += visible_pitch;
             }
             tc->vt->TexSubImage2D(tc->tex_target, 0, 0, 0, width, height,
                                   tex_format, tex_type, priv->texture_temp_buf);
@@ -487,11 +485,10 @@ upload_plane(const opengl_tex_converter_t *tc, unsigned tex_idx,
             tc->vt->TexSubImage2D(tc->tex_target, 0, 0, 0, width, height,
                                   tex_format, tex_type, pixels);
         }
-#undef ALIGN
     }
     else
     {
-        tc->vt->PixelStorei(GL_UNPACK_ROW_LENGTH, pitch / pixel_pitch);
+        tc->vt->PixelStorei(GL_UNPACK_ROW_LENGTH, pitch * width / visible_pitch);
         tc->vt->TexSubImage2D(tc->tex_target, 0, 0, 0, width, height,
                               tex_format, tex_type, pixels);
     }
@@ -515,7 +512,8 @@ tc_common_update(const opengl_tex_converter_t *tc, GLuint *textures,
                              pic->p[i].p_pixels;
 
         ret = upload_plane(tc, i, tex_width[i], tex_height[i],
-                           pic->p[i].i_pitch, pic->p[i].i_pixel_pitch, pixels);
+                           pic->p[i].i_pitch, pic->p[i].i_visible_pitch,
+                           pic->p[i].i_pixel_pitch, pixels);
     }
     return ret;
 }
diff --git a/modules/video_output/opengl/converter_vaapi.c b/modules/video_output/opengl/converter_vaapi.c
index 4e83ab09c5..635819d9f9 100644
--- a/modules/video_output/opengl/converter_vaapi.c
+++ b/modules/video_output/opengl/converter_vaapi.c
@@ -472,10 +472,6 @@ Open(vlc_object_t *obj)
     tc->pf_update  = tc_vaegl_update;
     tc->pf_get_pool = tc_vaegl_get_pool;
 
-    /* Fix the UV plane texture scale factor for GR */
-    if (vlc_sw_chroma == VLC_CODEC_NV12 || vlc_sw_chroma == VLC_CODEC_P010)
-        tc->texs[1].h = (vlc_rational_t) { 1, 2 };
-
     return VLC_SUCCESS;
 error:
     if (priv && priv->vainst)
diff --git a/modules/video_output/opengl/fragment_shaders.c b/modules/video_output/opengl/fragment_shaders.c
index a6cb68ddab..e24b080279 100644
--- a/modules/video_output/opengl/fragment_shaders.c
+++ b/modules/video_output/opengl/fragment_shaders.c
@@ -176,7 +176,7 @@ tc_yuv_base_init(opengl_tex_converter_t *tc, GLenum tex_target,
                 GL_UNSIGNED_BYTE
             };
             tc->texs[1] = (struct opengl_tex_cfg) {
-                { 1, 2 }, { 1, 4 }, twoplanes_texfmt, twoplanes_texfmt,
+                { 1, 2 }, { 1, 2 }, twoplanes_texfmt, twoplanes_texfmt,
                 GL_UNSIGNED_BYTE
             };
         }
@@ -191,7 +191,7 @@ tc_yuv_base_init(opengl_tex_converter_t *tc, GLenum tex_target,
                 GL_UNSIGNED_SHORT
             };
             tc->texs[1] = (struct opengl_tex_cfg) {
-                { 1, 2 }, { 1, 4 }, twoplanes16_texfmt, twoplanes_texfmt,
+                { 1, 2 }, { 1, 2 }, twoplanes16_texfmt, twoplanes_texfmt,
                 GL_UNSIGNED_SHORT
             };
         }



More information about the vlc-commits mailing list