Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(14)

Side by Side Diff: gpu/command_buffer/service/gles2_cmd_decoder.cc

Issue 2329453002: [Command buffer] During blit FB, It is invalid if src source and dst source have identical image (Closed)
Patch Set: addressed zmo@'s feedback: do not interate all drawbuffers to optimize the perf if possible Created 4 years, 3 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "gpu/command_buffer/service/gles2_cmd_decoder.h" 5 #include "gpu/command_buffer/service/gles2_cmd_decoder.h"
6 6
7 #include <limits.h> 7 #include <limits.h>
8 #include <stddef.h> 8 #include <stddef.h>
9 #include <stdint.h> 9 #include <stdint.h>
10 #include <stdio.h> 10 #include <stdio.h>
(...skipping 7583 matching lines...) Expand 10 before | Expand all | Expand 10 after
7594 } 7594 }
7595 7595
7596 GLsizei read_buffer_samples = GetBoundFramebufferSamples(GL_READ_FRAMEBUFFER); 7596 GLsizei read_buffer_samples = GetBoundFramebufferSamples(GL_READ_FRAMEBUFFER);
7597 if (read_buffer_samples > 0 && 7597 if (read_buffer_samples > 0 &&
7598 (srcX0 != dstX0 || srcY0 != dstY0 || srcX1 != dstX1 || srcY1 != dstY1)) { 7598 (srcX0 != dstX0 || srcY0 != dstY0 || srcX1 != dstX1 || srcY1 != dstY1)) {
7599 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, 7599 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name,
7600 "src framebuffer is multisampled, but src/dst regions are different"); 7600 "src framebuffer is multisampled, but src/dst regions are different");
7601 return; 7601 return;
7602 } 7602 }
7603 7603
7604 // Check whether read framebuffer and draw framebuffer have identical image
7605 enum FeedbackLoopState {
7606 FeedbackLoopTrue,
7607 FeedbackLoopFalse,
7608 FeedbackLoopUnknown
7609 };
7610
7611 FeedbackLoopState is_feedback_loop = FeedbackLoopUnknown;
7612 Framebuffer* read_framebuffer =
7613 framebuffer_state_.bound_read_framebuffer.get();
7614 Framebuffer* draw_framebuffer =
7615 framebuffer_state_.bound_draw_framebuffer.get();
7616 // If both read framebuffer and draw framebuffer are default framebuffer,
7617 // They always have identical image. Otherwise, if one of read framebuffer
7618 // and draw framebuffe is default framebuffer, but the other is fbo, they
7619 // always have no identical image.
7620 if (!read_framebuffer && !draw_framebuffer) {
7621 is_feedback_loop = FeedbackLoopTrue;
7622 } else if (!read_framebuffer || !draw_framebuffer) {
7623 is_feedback_loop = FeedbackLoopFalse;
7624 }
7625 if ((mask & GL_DEPTH_BUFFER_BIT) != 0) {
7626 const Framebuffer::Attachment* depth_buffer_read =
7627 read_framebuffer->GetAttachment(GL_DEPTH_ATTACHMENT);
7628 const Framebuffer::Attachment* depth_buffer_draw =
7629 draw_framebuffer->GetAttachment(GL_DEPTH_ATTACHMENT);
7630 if (depth_buffer_draw &&
7631 depth_buffer_draw->IsSameAttachment(depth_buffer_read)) {
7632 is_feedback_loop = FeedbackLoopTrue;
7633 }
7634 }
7635 if ((mask & GL_STENCIL_BUFFER_BIT) != 0) {
7636 const Framebuffer::Attachment* stencil_buffer_read =
7637 read_framebuffer->GetAttachment(GL_STENCIL_ATTACHMENT);
7638 const Framebuffer::Attachment* stencil_buffer_draw =
7639 draw_framebuffer->GetAttachment(GL_STENCIL_ATTACHMENT);
7640 if (stencil_buffer_draw &&
7641 stencil_buffer_draw->IsSameAttachment(stencil_buffer_read)) {
7642 is_feedback_loop = FeedbackLoopTrue;
7643 }
7644 }
7645
7604 GLenum src_format = GetBoundReadFramebufferInternalFormat(); 7646 GLenum src_format = GetBoundReadFramebufferInternalFormat();
7605 GLenum src_type = GetBoundReadFramebufferTextureType(); 7647 GLenum src_type = GetBoundReadFramebufferTextureType();
7606 7648
7607 if ((mask & GL_COLOR_BUFFER_BIT) != 0) { 7649 if ((mask & GL_COLOR_BUFFER_BIT) != 0) {
7608 bool is_src_signed_int = GLES2Util::IsSignedIntegerFormat(src_format); 7650 bool is_src_signed_int = GLES2Util::IsSignedIntegerFormat(src_format);
7609 bool is_src_unsigned_int = GLES2Util::IsUnsignedIntegerFormat(src_format); 7651 bool is_src_unsigned_int = GLES2Util::IsUnsignedIntegerFormat(src_format);
7610 DCHECK(!is_src_signed_int || !is_src_unsigned_int); 7652 DCHECK(!is_src_signed_int || !is_src_unsigned_int);
7611 7653
7612 if ((is_src_signed_int || is_src_unsigned_int) && filter == GL_LINEAR) { 7654 if ((is_src_signed_int || is_src_unsigned_int) && filter == GL_LINEAR) {
7613 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, 7655 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name,
7614 "invalid filter for integer format"); 7656 "invalid filter for integer format");
7615 return; 7657 return;
7616 } 7658 }
7617 7659
7618 GLenum src_sized_format = 7660 GLenum src_sized_format =
7619 GLES2Util::ConvertToSizedFormat(src_format, src_type); 7661 GLES2Util::ConvertToSizedFormat(src_format, src_type);
7662 const Framebuffer::Attachment* read_buffer =
7663 is_feedback_loop == FeedbackLoopUnknown ?
7664 read_framebuffer->GetReadBufferAttachment() : nullptr;
7620 for (uint32_t ii = 0; ii < group_->max_draw_buffers(); ++ii) { 7665 for (uint32_t ii = 0; ii < group_->max_draw_buffers(); ++ii) {
7621 GLenum dst_format = GetBoundColorDrawBufferInternalFormat( 7666 GLenum dst_format = GetBoundColorDrawBufferInternalFormat(
7622 static_cast<GLint>(ii)); 7667 static_cast<GLint>(ii));
7623 GLenum dst_type = GetBoundColorDrawBufferType(static_cast<GLint>(ii)); 7668 GLenum dst_type = GetBoundColorDrawBufferType(static_cast<GLint>(ii));
7624 if (dst_format == 0) 7669 if (dst_format == 0)
7625 continue; 7670 continue;
7626 if (read_buffer_samples > 0 && 7671 if (read_buffer_samples > 0 &&
7627 (src_sized_format != 7672 (src_sized_format !=
7628 GLES2Util::ConvertToSizedFormat(dst_format, dst_type))) { 7673 GLES2Util::ConvertToSizedFormat(dst_format, dst_type))) {
7629 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, 7674 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name,
7630 "src and dst formats differ for color"); 7675 "src and dst formats differ for color");
7631 return; 7676 return;
7632 } 7677 }
7633 bool is_dst_signed_int = GLES2Util::IsSignedIntegerFormat(dst_format); 7678 bool is_dst_signed_int = GLES2Util::IsSignedIntegerFormat(dst_format);
7634 bool is_dst_unsigned_int = GLES2Util::IsUnsignedIntegerFormat(dst_format); 7679 bool is_dst_unsigned_int = GLES2Util::IsUnsignedIntegerFormat(dst_format);
7635 DCHECK(!is_dst_signed_int || !is_dst_unsigned_int); 7680 DCHECK(!is_dst_signed_int || !is_dst_unsigned_int);
7636 if (is_src_signed_int != is_dst_signed_int || 7681 if (is_src_signed_int != is_dst_signed_int ||
7637 is_src_unsigned_int != is_dst_unsigned_int) { 7682 is_src_unsigned_int != is_dst_unsigned_int) {
7638 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, 7683 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name,
7639 "incompatible src/dst color formats"); 7684 "incompatible src/dst color formats");
7640 return; 7685 return;
7641 } 7686 }
7687 // Check whether draw buffers have identical color image with read buffer
7688 if (is_feedback_loop == FeedbackLoopUnknown) {
7689 GLenum drawbuffer = static_cast<GLenum>(GL_DRAW_BUFFER0 + ii);
7690 if (draw_framebuffer->GetDrawBuffer(drawbuffer) == GL_NONE) {
7691 continue;
7692 }
7693 GLenum attachment = static_cast<GLenum>(GL_COLOR_ATTACHMENT0 + ii);
7694 const Framebuffer::Attachment* draw_buffer =
7695 draw_framebuffer->GetAttachment(attachment);
7696 if (!draw_buffer) {
7697 continue;
7698 }
7699 if (draw_buffer->IsSameAttachment(read_buffer)) {
7700 is_feedback_loop = FeedbackLoopTrue;
Zhenyao Mo 2016/09/12 05:37:08 nit: break
yunchao 2016/09/12 06:01:51 Done.
7701 }
7702 }
7642 } 7703 }
7643 } 7704 }
7705 if (is_feedback_loop == FeedbackLoopTrue) {
7706 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name,
7707 "source buffer and destination buffers are identical");
7708 return;
7709 }
7644 7710
7645 if ((mask & (GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT)) != 0) { 7711 if ((mask & (GL_DEPTH_BUFFER_BIT | GL_STENCIL_BUFFER_BIT)) != 0) {
7646 if (filter != GL_NEAREST) { 7712 if (filter != GL_NEAREST) {
7647 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name, 7713 LOCAL_SET_GL_ERROR(GL_INVALID_OPERATION, func_name,
7648 "invalid filter for depth/stencil"); 7714 "invalid filter for depth/stencil");
7649 return; 7715 return;
7650 } 7716 }
7651 7717
7652 if ((GetBoundFramebufferDepthFormat(GL_READ_FRAMEBUFFER) != 7718 if ((GetBoundFramebufferDepthFormat(GL_READ_FRAMEBUFFER) !=
7653 GetBoundFramebufferDepthFormat(GL_DRAW_FRAMEBUFFER)) || 7719 GetBoundFramebufferDepthFormat(GL_DRAW_FRAMEBUFFER)) ||
(...skipping 10280 matching lines...) Expand 10 before | Expand all | Expand 10 after
17934 } 18000 }
17935 18001
17936 // Include the auto-generated part of this file. We split this because it means 18002 // Include the auto-generated part of this file. We split this because it means
17937 // we can easily edit the non-auto generated parts right here in this file 18003 // we can easily edit the non-auto generated parts right here in this file
17938 // instead of having to edit some template or the code generator. 18004 // instead of having to edit some template or the code generator.
17939 #include "base/macros.h" 18005 #include "base/macros.h"
17940 #include "gpu/command_buffer/service/gles2_cmd_decoder_autogen.h" 18006 #include "gpu/command_buffer/service/gles2_cmd_decoder_autogen.h"
17941 18007
17942 } // namespace gles2 18008 } // namespace gles2
17943 } // namespace gpu 18009 } // namespace gpu
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698