| Index: gpu/command_buffer/service/gles2_cmd_decoder.cc
|
| diff --git a/gpu/command_buffer/service/gles2_cmd_decoder.cc b/gpu/command_buffer/service/gles2_cmd_decoder.cc
|
| index c4918f32ba591c0e554c8896f9ca96a9ddb3ab71..a8b3b7032046a1f64fe8f52afde48882bc9189e5 100644
|
| --- a/gpu/command_buffer/service/gles2_cmd_decoder.cc
|
| +++ b/gpu/command_buffer/service/gles2_cmd_decoder.cc
|
| @@ -1270,12 +1270,12 @@ class GLES2DecoderImpl : public GLES2Decoder,
|
| bool ClearLevel(Texture* texture,
|
| unsigned target,
|
| int level,
|
| - unsigned internal_format,
|
| unsigned format,
|
| unsigned type,
|
| + int xoffset,
|
| + int yoffset,
|
| int width,
|
| - int height,
|
| - bool is_texture_immutable) override;
|
| + int height) override;
|
|
|
| // Restore all GL state that affects clearing.
|
| void RestoreClearState();
|
| @@ -3550,7 +3550,7 @@ bool GLES2DecoderImpl::CheckFramebufferValid(
|
|
|
| // Are all the attachments cleared?
|
| if (renderbuffer_manager()->HaveUnclearedRenderbuffers() ||
|
| - texture_manager()->HaveUnclearedMips()) {
|
| + texture_manager()->HaveUnsafeTextures()) {
|
| if (!framebuffer->IsCleared()) {
|
| // Can we clear them?
|
| if (framebuffer->GetStatus(texture_manager(), target) !=
|
| @@ -3685,17 +3685,12 @@ void GLES2DecoderImpl::UpdateParentTextureInfo() {
|
| GLenum target = offscreen_saved_color_texture_info_->texture()->target();
|
| glBindTexture(target, offscreen_saved_color_texture_info_->service_id());
|
| texture_manager()->SetLevelInfo(
|
| - offscreen_saved_color_texture_info_.get(),
|
| - GL_TEXTURE_2D,
|
| + offscreen_saved_color_texture_info_.get(), GL_TEXTURE_2D,
|
| 0, // level
|
| - GL_RGBA,
|
| - offscreen_size_.width(),
|
| - offscreen_size_.height(),
|
| + GL_RGBA, offscreen_size_.width(), offscreen_size_.height(),
|
| 1, // depth
|
| 0, // border
|
| - GL_RGBA,
|
| - GL_UNSIGNED_BYTE,
|
| - true);
|
| + GL_RGBA, GL_UNSIGNED_BYTE, gfx::Rect(offscreen_size_));
|
| texture_manager()->SetParameteri(
|
| "UpdateParentTextureInfo",
|
| GetErrorState(),
|
| @@ -8864,19 +8859,18 @@ void GLES2DecoderImpl::DoBufferSubData(
|
| &state_, target, offset, size, data);
|
| }
|
|
|
| -bool GLES2DecoderImpl::ClearLevel(
|
| - Texture* texture,
|
| - unsigned target,
|
| - int level,
|
| - unsigned internal_format,
|
| - unsigned format,
|
| - unsigned type,
|
| - int width,
|
| - int height,
|
| - bool is_texture_immutable) {
|
| +bool GLES2DecoderImpl::ClearLevel(Texture* texture,
|
| + unsigned target,
|
| + int level,
|
| + unsigned format,
|
| + unsigned type,
|
| + int xoffset,
|
| + int yoffset,
|
| + int width,
|
| + int height) {
|
| uint32 channels = GLES2Util::GetChannelsForFormat(format);
|
| if (feature_info_->feature_flags().angle_depth_texture &&
|
| - (channels & GLES2Util::kDepth) != 0) {
|
| + (channels & GLES2Util::kDepth) != 0 && xoffset == 0 && yoffset == 0) {
|
| // It's a depth format and ANGLE doesn't allow texImage2D or texSubImage2D
|
| // on depth formats.
|
| GLuint fb = 0;
|
| @@ -8949,17 +8943,11 @@ bool GLES2DecoderImpl::ClearLevel(
|
| memset(zero.get(), 0, size);
|
| glBindTexture(texture->target(), texture->service_id());
|
|
|
| - bool has_images = texture->HasImages();
|
| GLint y = 0;
|
| while (y < height) {
|
| GLint h = y + tile_height > height ? height - y : tile_height;
|
| - if (is_texture_immutable || h != height || has_images) {
|
| - glTexSubImage2D(target, level, 0, y, width, h, format, type, zero.get());
|
| - } else {
|
| - glTexImage2D(
|
| - target, level, internal_format, width, h, 0, format, type,
|
| - zero.get());
|
| - }
|
| + glTexSubImage2D(target, level, xoffset, yoffset + y, width, h, format, type,
|
| + zero.get());
|
| y += tile_height;
|
| }
|
| TextureRef* bound_texture =
|
| @@ -9320,9 +9308,9 @@ error::Error GLES2DecoderImpl::DoCompressedTexImage2D(
|
| target, level, internal_format, width, height, border, image_size, data);
|
| GLenum error = LOCAL_PEEK_GL_ERROR("glCompressedTexImage2D");
|
| if (error == GL_NO_ERROR) {
|
| - texture_manager()->SetLevelInfo(
|
| - texture_ref, target, level, internal_format,
|
| - width, height, 1, border, 0, 0, true);
|
| + texture_manager()->SetLevelInfo(texture_ref, target, level, internal_format,
|
| + width, height, 1, border, 0, 0,
|
| + gfx::Rect(width, height));
|
| }
|
|
|
| // This may be a slow command. Exit command processing to allow for
|
| @@ -9507,9 +9495,9 @@ error::Error GLES2DecoderImpl::DoCompressedTexImage3D(
|
| border, image_size, data);
|
| GLenum error = LOCAL_PEEK_GL_ERROR("glCompressedTexImage3D");
|
| if (error == GL_NO_ERROR) {
|
| - texture_manager()->SetLevelInfo(
|
| - texture_ref, target, level, internal_format,
|
| - width, height, depth, border, 0, 0, true);
|
| + texture_manager()->SetLevelInfo(texture_ref, target, level, internal_format,
|
| + width, height, depth, border, 0, 0,
|
| + gfx::Rect(width, height));
|
| }
|
|
|
| // This may be a slow command. Exit command processing to allow for
|
| @@ -9963,8 +9951,8 @@ void GLES2DecoderImpl::DoCopyTexImage2D(
|
| copyWidth != width ||
|
| copyHeight != height) {
|
| // some part was clipped so clear the texture.
|
| - if (!ClearLevel(texture, target, level, internal_format, internal_format,
|
| - GL_UNSIGNED_BYTE, width, height, texture->IsImmutable())) {
|
| + if (!ClearLevel(texture, target, level, internal_format, GL_UNSIGNED_BYTE,
|
| + 0, 0, width, height)) {
|
| LOCAL_SET_GL_ERROR(
|
| GL_OUT_OF_MEMORY, "glCopyTexImage2D", "dimensions too big");
|
| return;
|
| @@ -9986,9 +9974,9 @@ void GLES2DecoderImpl::DoCopyTexImage2D(
|
| }
|
| GLenum error = LOCAL_PEEK_GL_ERROR("glCopyTexImage2D");
|
| if (error == GL_NO_ERROR) {
|
| - texture_manager()->SetLevelInfo(
|
| - texture_ref, target, level, internal_format, width, height, 1,
|
| - border, internal_format, GL_UNSIGNED_BYTE, true);
|
| + texture_manager()->SetLevelInfo(texture_ref, target, level, internal_format,
|
| + width, height, 1, border, internal_format,
|
| + GL_UNSIGNED_BYTE, gfx::Rect(width, height));
|
| }
|
|
|
| // This may be a slow command. Exit command processing to allow for
|
| @@ -10076,6 +10064,8 @@ void GLES2DecoderImpl::DoCopyTexSubImage2D(
|
|
|
| if (xoffset != 0 || yoffset != 0 || width != size.width() ||
|
| height != size.height()) {
|
| + // TODO(reveman): Use SetLevelClearedRect when possible instead of clearing
|
| + // the texture prematurely.
|
| if (!texture_manager()->ClearTextureLevel(this, texture_ref, target,
|
| level)) {
|
| LOCAL_SET_GL_ERROR(GL_OUT_OF_MEMORY, "glCopyTexSubImage2D",
|
| @@ -10225,6 +10215,8 @@ error::Error GLES2DecoderImpl::DoTexSubImage2D(
|
| DCHECK(ok);
|
| if (xoffset != 0 || yoffset != 0 ||
|
| width != tex_width || height != tex_height) {
|
| + // TODO(reveman): Use SetLevelClearedRect when possible instead of clearing
|
| + // the texture prematurely.
|
| if (!texture_manager()->ClearTextureLevel(this, texture_ref,
|
| target, level)) {
|
| LOCAL_SET_GL_ERROR(
|
| @@ -11741,8 +11733,8 @@ void GLES2DecoderImpl::DoTexImageIOSurface2DCHROMIUM(
|
| }
|
|
|
| texture_manager()->SetLevelInfo(
|
| - texture_ref, target, 0, GL_RGBA, width, height, 1, 0,
|
| - GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV, true);
|
| + texture_ref, target, 0, GL_RGBA, width, height, 1, 0, GL_BGRA,
|
| + GL_UNSIGNED_INT_8_8_8_8_REV, gfx::Rect(width, height));
|
|
|
| #else
|
| LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION,
|
| @@ -11965,7 +11957,8 @@ void GLES2DecoderImpl::DoCopyTextureCHROMIUM(GLenum target,
|
|
|
| texture_manager()->SetLevelInfo(
|
| dest_texture_ref, GL_TEXTURE_2D, 0, internal_format, source_width,
|
| - source_height, 1, 0, internal_format, dest_type, true);
|
| + source_height, 1, 0, internal_format, dest_type,
|
| + gfx::Rect(source_width, source_height));
|
| } else {
|
| texture_manager()->SetLevelCleared(dest_texture_ref, GL_TEXTURE_2D, 0,
|
| true);
|
| @@ -12111,11 +12104,22 @@ void GLES2DecoderImpl::DoCopySubTextureCHROMIUM(GLenum target,
|
| DCHECK(ok);
|
| if (xoffset != 0 || yoffset != 0 || width != dest_width ||
|
| height != dest_height) {
|
| - if (!texture_manager()->ClearTextureLevel(this, dest_texture_ref, target,
|
| - 0)) {
|
| - LOCAL_SET_GL_ERROR(GL_OUT_OF_MEMORY, "glCopySubTextureCHROMIUM",
|
| - "destination texture dimensions too big");
|
| - return;
|
| + gfx::Rect cleared_rect(xoffset, yoffset, width, height);
|
| + gfx::Rect level_cleared_rect = dest_texture->GetLevelClearedRect(target, 0);
|
| + // Try to grow cleared rectangle.
|
| + if (level_cleared_rect.IsEmpty() ||
|
| + level_cleared_rect.SharesEdgeWith(cleared_rect)) {
|
| + cleared_rect.Union(level_cleared_rect);
|
| + texture_manager()->SetLevelClearedRect(dest_texture_ref, target, 0,
|
| + cleared_rect);
|
| + } else {
|
| + // Otherwise clear part of texture level that is not already cleared.
|
| + if (!texture_manager()->ClearTextureLevel(this, dest_texture_ref, target,
|
| + 0)) {
|
| + LOCAL_SET_GL_ERROR(GL_OUT_OF_MEMORY, "glCopySubTextureCHROMIUM",
|
| + "destination texture dimensions too big");
|
| + return;
|
| + }
|
| }
|
| } else {
|
| texture_manager()->SetLevelCleared(dest_texture_ref, GL_TEXTURE_2D, 0,
|
| @@ -12261,9 +12265,9 @@ void GLES2DecoderImpl::DoTexStorage2DEXT(
|
| GLsizei level_width = width;
|
| GLsizei level_height = height;
|
| for (int ii = 0; ii < levels; ++ii) {
|
| - texture_manager()->SetLevelInfo(
|
| - texture_ref, target, ii, format,
|
| - level_width, level_height, 1, 0, format, type, false);
|
| + texture_manager()->SetLevelInfo(texture_ref, target, ii, format,
|
| + level_width, level_height, 1, 0, format,
|
| + type, gfx::Rect());
|
| level_width = std::max(1, level_width >> 1);
|
| level_height = std::max(1, level_height >> 1);
|
| }
|
| @@ -12613,9 +12617,9 @@ void GLES2DecoderImpl::DoBindTexImage2DCHROMIUM(
|
|
|
| gfx::Size size = gl_image->GetSize();
|
| texture_manager()->SetLevelInfo(
|
| - texture_ref, target, 0, gl_image->GetInternalFormat(),
|
| - size.width(), size.height(), 1, 0,
|
| - gl_image->GetInternalFormat(), GL_UNSIGNED_BYTE, true);
|
| + texture_ref, target, 0, gl_image->GetInternalFormat(), size.width(),
|
| + size.height(), 1, 0, gl_image->GetInternalFormat(), GL_UNSIGNED_BYTE,
|
| + gfx::Rect(size));
|
| texture_manager()->SetLevelImage(texture_ref, target, 0, gl_image);
|
| }
|
|
|
| @@ -12654,7 +12658,7 @@ void GLES2DecoderImpl::DoReleaseTexImage2DCHROMIUM(
|
|
|
| texture_manager()->SetLevelInfo(
|
| texture_ref, target, 0, gl_image->GetInternalFormat(), 0, 0, 1, 0,
|
| - gl_image->GetInternalFormat(), GL_UNSIGNED_BYTE, false);
|
| + gl_image->GetInternalFormat(), GL_UNSIGNED_BYTE, gfx::Rect());
|
| }
|
|
|
| error::Error GLES2DecoderImpl::HandleTraceBeginCHROMIUM(
|
|
|