On Fri, Feb 27, 2015 at 4:07 PM, Laura Ekstrand <la...@jlekstrand.net> wrote: > --- > src/mesa/main/teximage.c | 204 > ++++++++++++++++++++++++++++++++++++++++------- > src/mesa/main/teximage.h | 3 +- > 2 files changed, 179 insertions(+), 28 deletions(-) > > diff --git a/src/mesa/main/teximage.c b/src/mesa/main/teximage.c > index dfad9ed..d454dd9 100644 > --- a/src/mesa/main/teximage.c > +++ b/src/mesa/main/teximage.c > @@ -4747,30 +4747,19 @@ _mesa_CompressedTexImage3D(GLenum target, GLint level, > void > _mesa_compressed_texture_sub_image(struct gl_context *ctx, GLuint dims, > struct gl_texture_object *texObj, > + struct gl_texture_image *texImage, > GLenum target, GLint level, > GLint xoffset, GLint yoffset, > GLint zoffset, > GLsizei width, GLsizei height, > GLsizei depth, > GLenum format, GLsizei imageSize, > - const GLvoid *data, bool dsa) > + const GLvoid *data) > { > - struct gl_texture_image *texImage; > - > - if (compressed_subtexture_error_check(ctx, dims, texObj, target, > - level, xoffset, yoffset, zoffset, > - width, height, depth, > - format, imageSize, dsa)) { > - return; > - } > - > FLUSH_VERTICES(ctx, 0); > > _mesa_lock_texture(ctx, texObj); > { > - texImage = _mesa_select_tex_image(texObj, target, level); > - assert(texImage); > - > if (width > 0 && height > 0 && depth > 0) { > ctx->Driver.CompressedTexSubImage(ctx, dims, texImage, > xoffset, yoffset, zoffset, > @@ -4794,6 +4783,8 @@ _mesa_CompressedTexSubImage1D(GLenum target, GLint > level, GLint xoffset, > GLsizei imageSize, const GLvoid *data) > { > struct gl_texture_object *texObj; > + struct gl_texture_image *texImage; > + > GET_CURRENT_CONTEXT(ctx); > > if (compressed_subtexture_target_check(ctx, target, 1, format, false, > @@ -4805,9 +4796,20 @@ _mesa_CompressedTexSubImage1D(GLenum target, GLint > level, GLint xoffset, > if (!texObj) > return; > > - _mesa_compressed_texture_sub_image(ctx, 1, texObj, target, level, > + if (compressed_subtexture_error_check(ctx, 1, texObj, target, > + level, xoffset, 0, 0, > + width, 1, 1, > + format, imageSize, false)) { > + return; > + } > + > + texImage = _mesa_select_tex_image(texObj, target, level); > + if (!texImage) > + return; > + compressed_subtexture_error_check() already does this check. Instead add assert(texImage) here and all other places in this patch. Otherwise patch looks good to me.
> + _mesa_compressed_texture_sub_image(ctx, 1, texObj, texImage, target, > level, > xoffset, 0, 0, width, 1, 1, > - format, imageSize, data, false); > + format, imageSize, data); > } > > void GLAPIENTRY > @@ -4816,6 +4818,8 @@ _mesa_CompressedTextureSubImage1D(GLuint texture, GLint > level, GLint xoffset, > GLsizei imageSize, const GLvoid *data) > { > struct gl_texture_object *texObj; > + struct gl_texture_image *texImage; > + > GET_CURRENT_CONTEXT(ctx); > > texObj = _mesa_lookup_texture_err(ctx, texture, > @@ -4829,9 +4833,21 @@ _mesa_CompressedTextureSubImage1D(GLuint texture, > GLint level, GLint xoffset, > return; > } > > - _mesa_compressed_texture_sub_image(ctx, 1, texObj, texObj->Target, level, > + if (compressed_subtexture_error_check(ctx, 1, texObj, texObj->Target, > + level, xoffset, 0, 0, > + width, 1, 1, > + format, imageSize, true)) { > + return; > + } > + > + texImage = _mesa_select_tex_image(texObj, texObj->Target, level); > + if (!texImage) > + return; > + > + _mesa_compressed_texture_sub_image(ctx, 1, texObj, texImage, > + texObj->Target, level, > xoffset, 0, 0, width, 1, 1, > - format, imageSize, data, true); > + format, imageSize, data); > } > > > @@ -4842,6 +4858,8 @@ _mesa_CompressedTexSubImage2D(GLenum target, GLint > level, GLint xoffset, > const GLvoid *data) > { > struct gl_texture_object *texObj; > + struct gl_texture_image *texImage; > + > GET_CURRENT_CONTEXT(ctx); > > if (compressed_subtexture_target_check(ctx, target, 2, format, false, > @@ -4853,9 +4871,21 @@ _mesa_CompressedTexSubImage2D(GLenum target, GLint > level, GLint xoffset, > if (!texObj) > return; > > - _mesa_compressed_texture_sub_image(ctx, 2, texObj, target, level, > + if (compressed_subtexture_error_check(ctx, 2, texObj, target, > + level, xoffset, yoffset, 0, > + width, height, 1, > + format, imageSize, false)) { > + return; > + } > + > + > + texImage = _mesa_select_tex_image(texObj, target, level); > + if (!texImage) > + return; > + > + _mesa_compressed_texture_sub_image(ctx, 2, texObj, texImage, target, > level, > xoffset, yoffset, 0, width, height, 1, > - format, imageSize, data, false); > + format, imageSize, data); > } > > void GLAPIENTRY > @@ -4866,6 +4896,8 @@ _mesa_CompressedTextureSubImage2D(GLuint texture, GLint > level, GLint xoffset, > const GLvoid *data) > { > struct gl_texture_object *texObj; > + struct gl_texture_image *texImage; > + > GET_CURRENT_CONTEXT(ctx); > > texObj = _mesa_lookup_texture_err(ctx, texture, > @@ -4879,9 +4911,21 @@ _mesa_CompressedTextureSubImage2D(GLuint texture, > GLint level, GLint xoffset, > return; > } > > - _mesa_compressed_texture_sub_image(ctx, 2, texObj, texObj->Target, level, > + if (compressed_subtexture_error_check(ctx, 2, texObj, texObj->Target, > + level, xoffset, yoffset, 0, > + width, height, 1, > + format, imageSize, true)) { > + return; > + } > + > + texImage = _mesa_select_tex_image(texObj, texObj->Target, level); > + if (!texImage) > + return; > + > + _mesa_compressed_texture_sub_image(ctx, 2, texObj, texImage, > + texObj->Target, level, > xoffset, yoffset, 0, width, height, 1, > - format, imageSize, data, true); > + format, imageSize, data); > } > > void GLAPIENTRY > @@ -4891,6 +4935,8 @@ _mesa_CompressedTexSubImage3D(GLenum target, GLint > level, GLint xoffset, > GLsizei imageSize, const GLvoid *data) > { > struct gl_texture_object *texObj; > + struct gl_texture_image *texImage; > + > GET_CURRENT_CONTEXT(ctx); > > if (compressed_subtexture_target_check(ctx, target, 3, format, false, > @@ -4902,10 +4948,22 @@ _mesa_CompressedTexSubImage3D(GLenum target, GLint > level, GLint xoffset, > if (!texObj) > return; > > - _mesa_compressed_texture_sub_image(ctx, 3, texObj, target, level, > + if (compressed_subtexture_error_check(ctx, 3, texObj, target, > + level, xoffset, yoffset, zoffset, > + width, height, depth, > + format, imageSize, false)) { > + return; > + } > + > + > + texImage = _mesa_select_tex_image(texObj, target, level); > + if (!texImage) > + return; > + > + _mesa_compressed_texture_sub_image(ctx, 3, texObj, texImage, target, > level, > xoffset, yoffset, zoffset, > width, height, depth, > - format, imageSize, data, false); > + format, imageSize, data); > } > > void GLAPIENTRY > @@ -4916,6 +4974,8 @@ _mesa_CompressedTextureSubImage3D(GLuint texture, GLint > level, GLint xoffset, > const GLvoid *data) > { > struct gl_texture_object *texObj; > + struct gl_texture_image *texImage; > + > GET_CURRENT_CONTEXT(ctx); > > texObj = _mesa_lookup_texture_err(ctx, texture, > @@ -4929,10 +4989,100 @@ _mesa_CompressedTextureSubImage3D(GLuint texture, > GLint level, GLint xoffset, > return; > } > > - _mesa_compressed_texture_sub_image(ctx, 3, texObj, texObj->Target, level, > - xoffset, yoffset, zoffset, > - width, height, depth, > - format, imageSize, data, true); > + if (compressed_subtexture_error_check(ctx, 3, texObj, texObj->Target, > + level, xoffset, yoffset, zoffset, > + width, height, depth, > + format, imageSize, true)) { > + return; > + } > + > + /* Must handle special case GL_TEXTURE_CUBE_MAP. */ > + if (texObj->Target == GL_TEXTURE_CUBE_MAP) { > + const char *pixels = data; > + int i; > + GLint image_stride; > + > + /* Error checking */ > + if (texObj->NumLayers < 6) { > + /* Not enough image planes for a cube map. The spec does not say > + * what should happen in this case because the user has always > + * specified each cube face separately (using > + * GL_TEXTURE_CUBE_MAP_POSITIVE_X+i) in previous GL versions. > + * This is addressed in Khronos Bug 13223. > + */ > + _mesa_error(ctx, GL_INVALID_OPERATION, > + "glCompressedTextureSubImage3D" > + "(insufficient cube map storage)"); > + return; > + } > + > + /* > + * What do we do if the user created a texture with the following code > + * and then called this function with its handle? > + * > + * GLuint tex; > + * glCreateTextures(GL_TEXTURE_CUBE_MAP, 1, &tex); > + * glBindTexture(GL_TEXTURE_CUBE_MAP, tex); > + * glCompressedTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_X, 0, ...); > + * glCompressedTexImage2D(GL_TEXTURE_CUBE_MAP_NEGATIVE_X, 0, ...); > + * glCompressedTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_Y, 0, ...); > + * // Note: GL_TEXTURE_CUBE_MAP_NEGATIVE_Y not set, or given the > + * // wrong format, or given the wrong size, etc. > + * glCompressedTexImage2D(GL_TEXTURE_CUBE_MAP_POSITIVE_Z, 0, ...); > + * glCompressedTexImage2D(GL_TEXTURE_CUBE_MAP_NEGATIVE_Z, 0, ...); > + * > + * A bug has been filed against the spec for this case. In the > + * meantime, we will check for cube completeness. > + * > + * According to Section 8.17 Texture Completeness in the OpenGL 4.5 > + * Core Profile spec (30.10.2014): > + * "[A] cube map texture is cube complete if the > + * following conditions all hold true: The [base level] texture > + * images of each of the six cube map faces have identical, > positive, > + * and square dimensions. The [base level] images were each > specified > + * with the same internal format." > + * > + * It seems reasonable to check for cube completeness of an arbitrary > + * level here so that the image data has a consistent format and size. > + */ > + if (!_mesa_cube_level_complete(texObj, level)) { > + _mesa_error(ctx, GL_INVALID_OPERATION, > + "glCompressedTextureSubImage3D(cube map incomplete)"); > + return; > + } > + > + /* Copy in each face. */ > + for (i = 0; i < 6; ++i) { > + texImage = texObj->Image[i][level]; > + if (!texImage) > + return; > + > + _mesa_compressed_texture_sub_image(ctx, 3, texObj, texImage, > + texObj->Target, level, > + xoffset, yoffset, zoffset, > + width, height, 1, > + format, imageSize, pixels); > + > + /* Compressed images don't have a client format */ > + image_stride = _mesa_format_image_size(texImage->TexFormat, > + texImage->Width, > + texImage->Height, 1); > + > + pixels += image_stride; > + imageSize -= image_stride; > + } > + } > + else { > + texImage = _mesa_select_tex_image(texObj, texObj->Target, level); > + if (!texImage) > + return; > + > + _mesa_compressed_texture_sub_image(ctx, 3, texObj, texImage, > + texObj->Target, level, > + xoffset, yoffset, zoffset, > + width, height, depth, > + format, imageSize, data); > + } > } > > static mesa_format > diff --git a/src/mesa/main/teximage.h b/src/mesa/main/teximage.h > index b7336bc..9468650 100644 > --- a/src/mesa/main/teximage.h > +++ b/src/mesa/main/teximage.h > @@ -181,13 +181,14 @@ _mesa_texture_sub_image(struct gl_context *ctx, GLuint > dims, > extern void > _mesa_compressed_texture_sub_image(struct gl_context *ctx, GLuint dims, > struct gl_texture_object *texObj, > + struct gl_texture_image *texImage, > GLenum target, GLint level, > GLint xoffset, GLint yoffset, > GLint zoffset, > GLsizei width, GLsizei height, > GLsizei depth, > GLenum format, GLsizei imageSize, > - const GLvoid *data, bool dsa); > + const GLvoid *data); > > extern void > _mesa_copy_texture_sub_image(struct gl_context *ctx, GLuint dims, > -- > 2.1.0 > > _______________________________________________ > mesa-dev mailing list > mesa-dev@lists.freedesktop.org > http://lists.freedesktop.org/mailman/listinfo/mesa-dev _______________________________________________ mesa-dev mailing list mesa-dev@lists.freedesktop.org http://lists.freedesktop.org/mailman/listinfo/mesa-dev