[Mesa-dev] [PATCH 04/11] mesa: plumb offset/size parameters through GetTexImage code

Laura Ekstrand laura at jlekstrand.net
Tue Dec 16 14:22:40 PST 2014


On Sat, Dec 13, 2014 at 6:42 AM, Brian Paul <brianp at vmware.com> wrote:
>
> Needed for GL_ARB_get_texture_sub_image.  But at this point, the
> offsets are always zero and the sizes match the whole texture image.
> ---
>  src/mesa/main/texgetimage.c | 105
> ++++++++++++++++++++++++--------------------
>  1 file changed, 58 insertions(+), 47 deletions(-)
>
> diff --git a/src/mesa/main/texgetimage.c b/src/mesa/main/texgetimage.c
> index 03ad5f4..71c25bb 100644
> --- a/src/mesa/main/texgetimage.c
> +++ b/src/mesa/main/texgetimage.c
> @@ -74,12 +74,11 @@ type_needs_clamping(GLenum type)
>   */
>  static void
>  get_tex_depth(struct gl_context *ctx, GLuint dimensions,
> +              GLint xoffset, GLint yoffset, GLint zoffset,
> +              GLsizei width, GLsizei height, GLint depth,
>                GLenum format, GLenum type, GLvoid *pixels,
>                struct gl_texture_image *texImage)
>  {
> -   const GLint width = texImage->Width;
> -   GLint height = texImage->Height;
> -   GLint depth = texImage->Depth;
>     GLint img, row;
>     GLfloat *depthRow = malloc(width * sizeof(GLfloat));
>
> @@ -98,9 +97,9 @@ get_tex_depth(struct gl_context *ctx, GLuint dimensions,
>        GLint srcRowStride;

You are not checking here to make sure that zoffset + img < depth.  I
looked in the next patch (implement _mesa_GetTextureSubImage) and found
that the dimensions_error_check does this.  It might be good to make a note
of that here.

       /* map src texture buffer */
> -      ctx->Driver.MapTextureImage(ctx, texImage, img,
> -                                  0, 0, width, height, GL_MAP_READ_BIT,
> -                                &srcMap, &srcRowStride);
> +      ctx->Driver.MapTextureImage(ctx, texImage, zoffset + img,
> +                                  xoffset, yoffset, width, height,
> +                                  GL_MAP_READ_BIT, &srcMap,
> &srcRowStride);
>
>        if (srcMap) {
>           for (row = 0; row < height; row++) {
>
Why didn't you update ctx->Driver.UnmapTextureImage(ctx, texImage, img) to
take zoffset + img here?  You did that for get_tex_rgba_uncompressed.  Is
there some reason that it has to be UnmapTextureImage(.. img only) for all
of the other functions?


> @@ -129,12 +128,11 @@ get_tex_depth(struct gl_context *ctx, GLuint
> dimensions,
>   */
>  static void
>  get_tex_depth_stencil(struct gl_context *ctx, GLuint dimensions,
> +                      GLint xoffset, GLint yoffset, GLint zoffset,
> +                      GLsizei width, GLsizei height, GLint depth,
>                        GLenum format, GLenum type, GLvoid *pixels,
>                        struct gl_texture_image *texImage)
>  {
> -   const GLint width = texImage->Width;
> -   const GLint height = texImage->Height;
> -   const GLint depth = texImage->Depth;
>     GLint img, row;
>
>     assert(format == GL_DEPTH_STENCIL);
> @@ -146,9 +144,9 @@ get_tex_depth_stencil(struct gl_context *ctx, GLuint
> dimensions,
>        GLint rowstride;
>
>        /* map src texture buffer */
> -      ctx->Driver.MapTextureImage(ctx, texImage, img,
> -                                  0, 0, width, height, GL_MAP_READ_BIT,
> -                                  &srcMap, &rowstride);
> +      ctx->Driver.MapTextureImage(ctx, texImage, zoffset + img,
> +                                  xoffset, yoffset, width, height,
> +                                  GL_MAP_READ_BIT, &srcMap, &rowstride);
>
>        if (srcMap) {
>           for (row = 0; row < height; row++) {
> @@ -180,12 +178,11 @@ get_tex_depth_stencil(struct gl_context *ctx, GLuint
> dimensions,
>   */
>  static void
>  get_tex_ycbcr(struct gl_context *ctx, GLuint dimensions,
> +              GLint xoffset, GLint yoffset, GLint zoffset,
> +              GLsizei width, GLsizei height, GLint depth,
>                GLenum format, GLenum type, GLvoid *pixels,
>                struct gl_texture_image *texImage)
>  {
> -   const GLint width = texImage->Width;
> -   const GLint height = texImage->Height;
> -   const GLint depth = texImage->Depth;
>     GLint img, row;
>
>     for (img = 0; img < depth; img++) {
> @@ -193,9 +190,9 @@ get_tex_ycbcr(struct gl_context *ctx, GLuint
> dimensions,
>        GLint rowstride;
>
>        /* map src texture buffer */
> -      ctx->Driver.MapTextureImage(ctx, texImage, img,
> -                                  0, 0, width, height, GL_MAP_READ_BIT,
> -                                  &srcMap, &rowstride);
> +      ctx->Driver.MapTextureImage(ctx, texImage, zoffset + img,
> +                                  xoffset, yoffset, width, height,
> +                                  GL_MAP_READ_BIT, &srcMap, &rowstride);
>
>        if (srcMap) {
>           for (row = 0; row < height; row++) {
> @@ -233,6 +230,8 @@ get_tex_ycbcr(struct gl_context *ctx, GLuint
> dimensions,
>   */
>  static void
>  get_tex_rgba_compressed(struct gl_context *ctx, GLuint dimensions,
> +                        GLint xoffset, GLint yoffset, GLint zoffset,
> +                        GLsizei width, GLsizei height, GLint depth,
>                          GLenum format, GLenum type, GLvoid *pixels,
>                          struct gl_texture_image *texImage,
>                          GLbitfield transferOps)
> @@ -243,9 +242,6 @@ get_tex_rgba_compressed(struct gl_context *ctx, GLuint
> dimensions,
>     const GLenum baseFormat = _mesa_get_format_base_format(texFormat);
>     const GLenum destBaseFormat = _mesa_base_tex_format(ctx, format);
>     GLenum rebaseFormat = GL_NONE;
> -   const GLuint width = texImage->Width;
> -   const GLuint height = texImage->Height;
> -   const GLuint depth = texImage->Depth;
>     GLfloat *tempImage, *tempSlice, *srcRow;
>     GLuint row, slice;
>
> @@ -264,8 +260,8 @@ get_tex_rgba_compressed(struct gl_context *ctx, GLuint
> dimensions,
>
>        tempSlice = tempImage + slice * 4 * width * height;
>
> -      ctx->Driver.MapTextureImage(ctx, texImage, slice,
> -                                  0, 0, width, height,
> +      ctx->Driver.MapTextureImage(ctx, texImage, zoffset + slice,
> +                                  xoffset, yoffset, width, height,
>                                    GL_MAP_READ_BIT,
>                                    &srcMap, &srcRowStride);
>        if (srcMap) {
> @@ -368,6 +364,8 @@ _mesa_base_pack_format(GLenum format)
>   */
>  static void
>  get_tex_rgba_uncompressed(struct gl_context *ctx, GLuint dimensions,
> +                          GLint xoffset, GLint yoffset, GLint zoffset,
> +                          GLsizei width, GLsizei height, GLint depth,
>                            GLenum format, GLenum type, GLvoid *pixels,
>                            struct gl_texture_image *texImage,
>                            GLbitfield transferOps)
> @@ -375,11 +373,8 @@ get_tex_rgba_uncompressed(struct gl_context *ctx,
> GLuint dimensions,
>     /* don't want to apply sRGB -> RGB conversion here so override the
> format */
>     const mesa_format texFormat =
>        _mesa_get_srgb_format_linear(texImage->TexFormat);
> -   const GLuint width = texImage->Width;
>     GLenum destBaseFormat = _mesa_base_pack_format(format);
>     GLenum rebaseFormat = GL_NONE;
> -   GLuint height = texImage->Height;
> -   GLuint depth = texImage->Depth;
>     GLuint img, row;
>     GLfloat (*rgba)[4];
>     GLuint (*rgba_uint)[4];
> @@ -472,9 +467,9 @@ get_tex_rgba_uncompressed(struct gl_context *ctx,
> GLuint dimensions,
>        GLint rowstride;
>
>        /* map src texture buffer */
> -      ctx->Driver.MapTextureImage(ctx, texImage, img,
> -                                  0, 0, width, height, GL_MAP_READ_BIT,
> -                                  &srcMap, &rowstride);
> +      ctx->Driver.MapTextureImage(ctx, texImage, zoffset + img,
> +                                  xoffset, yoffset, width, height,
> +                                  GL_MAP_READ_BIT, &srcMap, &rowstride);
>        if (srcMap) {
>           for (row = 0; row < height; row++) {
>              const GLubyte *src = srcMap + row * rowstride;
> @@ -506,7 +501,7 @@ get_tex_rgba_uncompressed(struct gl_context *ctx,
> GLuint dimensions,
>          }
>
>           /* Unmap the src texture buffer */
> -         ctx->Driver.UnmapTextureImage(ctx, texImage, img);
> +         ctx->Driver.UnmapTextureImage(ctx, texImage, zoffset + img);
>        }
>        else {
>           _mesa_error(ctx, GL_OUT_OF_MEMORY, "glGetTexImage");
> @@ -524,6 +519,8 @@ get_tex_rgba_uncompressed(struct gl_context *ctx,
> GLuint dimensions,
>   */
>  static void
>  get_tex_rgba(struct gl_context *ctx, GLuint dimensions,
> +             GLint xoffset, GLint yoffset, GLint zoffset,
> +             GLsizei width, GLsizei height, GLint depth,
>               GLenum format, GLenum type, GLvoid *pixels,
>               struct gl_texture_image *texImage)
>  {
> @@ -545,11 +542,17 @@ get_tex_rgba(struct gl_context *ctx, GLuint
> dimensions,
>     }
>
>     if (_mesa_is_format_compressed(texImage->TexFormat)) {
> -      get_tex_rgba_compressed(ctx, dimensions, format, type,
> +      get_tex_rgba_compressed(ctx, dimensions,
> +                              xoffset, yoffset, zoffset,
> +                              width, height, depth,
> +                              format, type,
>                                pixels, texImage, transferOps);
>     }
>     else {
> -      get_tex_rgba_uncompressed(ctx, dimensions, format, type,
> +      get_tex_rgba_uncompressed(ctx, dimensions,
> +                                xoffset, yoffset, zoffset,
> +                                width, height, depth,
> +                                format, type,
>                                  pixels, texImage, transferOps);
>     }
>  }
> @@ -560,8 +563,10 @@ get_tex_rgba(struct gl_context *ctx, GLuint
> dimensions,
>   * \return GL_TRUE if done, GL_FALSE otherwise
>   */
>  static GLboolean
> -get_tex_memcpy(struct gl_context *ctx, GLenum format, GLenum type,
> -               GLvoid *pixels,
> +get_tex_memcpy(struct gl_context *ctx,
> +               GLint xoffset, GLint yoffset, GLint zoffset,
> +               GLsizei width, GLsizei height, GLint depth,
> +               GLenum format, GLenum type, GLvoid *pixels,
>                 struct gl_texture_image *texImage)
>  {
>     const GLenum target = texImage->TexObject->Target;
> @@ -585,27 +590,27 @@ get_tex_memcpy(struct gl_context *ctx, GLenum
> format, GLenum type,
>
>     if (memCopy) {
>        const GLuint bpp = _mesa_get_format_bytes(texImage->TexFormat);
> -      const GLuint bytesPerRow = texImage->Width * bpp;
> +      const GLuint bytesPerRow = width * bpp;
>        GLubyte *dst =
> -         _mesa_image_address2d(&ctx->Pack, pixels, texImage->Width,
> -                               texImage->Height, format, type, 0, 0);
> +         _mesa_image_address2d(&ctx->Pack, pixels, width, height,
> +                               format, type, 0, 0);
>        const GLint dstRowStride =
> -         _mesa_image_row_stride(&ctx->Pack, texImage->Width, format,
> type);
> +         _mesa_image_row_stride(&ctx->Pack, width, format, type);
>        GLubyte *src;
>        GLint srcRowStride;
>
>        /* map src texture buffer */
> -      ctx->Driver.MapTextureImage(ctx, texImage, 0,
> -                                  0, 0, texImage->Width, texImage->Height,
> +      ctx->Driver.MapTextureImage(ctx, texImage, zoffset,
> +                                  xoffset, yoffset, width, height,
>                                    GL_MAP_READ_BIT, &src, &srcRowStride);
>
>        if (src) {
>           if (bytesPerRow == dstRowStride && bytesPerRow == srcRowStride) {
> -            memcpy(dst, src, bytesPerRow * texImage->Height);
> +            memcpy(dst, src, bytesPerRow * height);
>           }
>           else {
>              GLuint row;
> -            for (row = 0; row < texImage->Height; row++) {
> +            for (row = 0; row < height; row++) {
>                 memcpy(dst, src, bytesPerRow);
>                 dst += dstRowStride;
>                 src += srcRowStride;
> @@ -663,20 +668,26 @@ _mesa_get_texsubimage(struct gl_context *ctx,
>        pixels = ADD_POINTERS(buf, pixels);
>     }
>
> -   if (get_tex_memcpy(ctx, format, type, pixels, texImage)) {
> +   if (get_tex_memcpy(ctx, xoffset, yoffset, zoffset, width, height,
> depth,
> +                      format, type, pixels, texImage)) {
>        /* all done */
>     }
>     else if (format == GL_DEPTH_COMPONENT) {
> -      get_tex_depth(ctx, dimensions, format, type, pixels, texImage);
> +      get_tex_depth(ctx, dimensions, xoffset, yoffset, zoffset,
> +                    width, height, depth, format, type, pixels, texImage);
>     }
>     else if (format == GL_DEPTH_STENCIL_EXT) {
> -      get_tex_depth_stencil(ctx, dimensions, format, type, pixels,
> texImage);
> +      get_tex_depth_stencil(ctx, dimensions, xoffset, yoffset, zoffset,
> +                            width, height, depth,
> +                            format, type, pixels, texImage);
>     }
>     else if (format == GL_YCBCR_MESA) {
> -      get_tex_ycbcr(ctx, dimensions, format, type, pixels, texImage);
> +      get_tex_ycbcr(ctx, dimensions, xoffset, yoffset, zoffset,
> +                    width, height, depth, format, type, pixels, texImage);
>     }
>     else {
> -      get_tex_rgba(ctx, dimensions, format, type, pixels, texImage);
> +      get_tex_rgba(ctx, dimensions, xoffset, yoffset, zoffset,
> +                   width, height, depth, format, type, pixels, texImage);
>     }
>
>     if (_mesa_is_bufferobj(ctx->Pack.BufferObj)) {
> --
> 1.9.1
>
> _______________________________________________
> mesa-dev mailing list
> mesa-dev at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/mesa-dev
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.freedesktop.org/archives/mesa-dev/attachments/20141216/312f58f4/attachment-0001.html>


More information about the mesa-dev mailing list