[Mesa-dev] [PATCH 4/6] intel: Fix framebuffer blitting to GL_COLOR_ATTACHMENTi when i!=0
Ian Romanick
idr at freedesktop.org
Tue Dec 18 11:20:35 PST 2012
On 12/12/2012 03:25 PM, Anuj Phogat wrote:
> This patch fixes a case when blitting to a framebuffer with
> renderbuffers/textures attached to GL_COLOR_ATTACHMENT{1, 2, ...}.
> Earlier we were incorrectly blitting to GL_COLOR_ATTACHMENT0 by default.
>
> Signed-off-by: Anuj Phogat <anuj.phogat at gmail.com>
> ---
> src/mesa/drivers/dri/i965/brw_blorp_blit.cpp | 5 +-
> src/mesa/drivers/dri/intel/intel_fbo.c | 85 ++++++++++++++++----------
> 2 files changed, 56 insertions(+), 34 deletions(-)
>
> diff --git a/src/mesa/drivers/dri/i965/brw_blorp_blit.cpp b/src/mesa/drivers/dri/i965/brw_blorp_blit.cpp
> index e8604e7..41a8734 100644
> --- a/src/mesa/drivers/dri/i965/brw_blorp_blit.cpp
> +++ b/src/mesa/drivers/dri/i965/brw_blorp_blit.cpp
> @@ -263,8 +263,9 @@ try_blorp_blit(struct intel_context *intel,
> }
> for (unsigned i = 0; i < ctx->DrawBuffer->_NumColorDrawBuffers; ++i) {
> dst_irb = intel_renderbuffer(ctx->DrawBuffer->_ColorDrawBuffers[i]);
> - do_blorp_blit(intel, buffer_bit, src_irb, dst_irb, srcX0, srcY0,
> - dstX0, dstY0, dstX1, dstY1, mirror_x, mirror_y);
> + if (dst_irb)
> + do_blorp_blit(intel, buffer_bit, src_irb, dst_irb, srcX0, srcY0,
> + dstX0, dstY0, dstX1, dstY1, mirror_x, mirror_y);
> }
> break;
> case GL_DEPTH_BUFFER_BIT:
> diff --git a/src/mesa/drivers/dri/intel/intel_fbo.c b/src/mesa/drivers/dri/intel/intel_fbo.c
> index 6a66521..d0e9fe2 100644
> --- a/src/mesa/drivers/dri/intel/intel_fbo.c
> +++ b/src/mesa/drivers/dri/intel/intel_fbo.c
> @@ -793,44 +793,65 @@ intel_blit_framebuffer_copy_tex_sub_image(struct gl_context *ctx,
> GLbitfield mask, GLenum filter)
> {
> if (mask & GL_COLOR_BUFFER_BIT) {
> + GLboolean result = false;
Use bool.
> const struct gl_framebuffer *drawFb = ctx->DrawBuffer;
> const struct gl_framebuffer *readFb = ctx->ReadBuffer;
> - const struct gl_renderbuffer_attachment *drawAtt =
> - &drawFb->Attachment[drawFb->_ColorDrawBufferIndexes[0]];
> + const struct gl_renderbuffer_attachment *drawAtt;
> struct intel_renderbuffer *srcRb =
> intel_renderbuffer(readFb->_ColorReadBuffer);
>
> - /* If the source and destination are the same size with no
> - mirroring, the rectangles are within the size of the
> - texture and there is no scissor then we can use
> - glCopyTexSubimage2D to implement the blit. This will end
> - up as a fast hardware blit on some drivers */
> - if (srcRb && drawAtt && drawAtt->Texture &&
> - srcX0 - srcX1 == dstX0 - dstX1 &&
> - srcY0 - srcY1 == dstY0 - dstY1 &&
> - srcX1 >= srcX0 &&
> - srcY1 >= srcY0 &&
> - srcX0 >= 0 && srcX1 <= readFb->Width &&
> - srcY0 >= 0 && srcY1 <= readFb->Height &&
> - dstX0 >= 0 && dstX1 <= drawFb->Width &&
> - dstY0 >= 0 && dstY1 <= drawFb->Height &&
> - !ctx->Scissor.Enabled) {
> - const struct gl_texture_object *texObj = drawAtt->Texture;
> - const GLuint dstLevel = drawAtt->TextureLevel;
> - const GLenum target = texObj->Target;
> -
> - struct gl_texture_image *texImage =
> - _mesa_select_tex_image(ctx, texObj, target, dstLevel);
> -
> - if (intel_copy_texsubimage(intel_context(ctx),
> - intel_texture_image(texImage),
> - dstX0, dstY0,
> - srcRb,
> - srcX0, srcY0,
> - srcX1 - srcX0, /* width */
> - srcY1 - srcY0))
> - mask &= ~GL_COLOR_BUFFER_BIT;
> + /* Blit to all active draw buffers */
> + for (int i = 0; i < ctx->DrawBuffer->_NumColorDrawBuffers; i++) {
> + int idx = ctx->DrawBuffer->_ColorDrawBufferIndexes[i];
> + if (idx != -1) {
> + drawAtt = &drawFb->Attachment[idx];
> + }
> + else
> + continue;
if (idx == -1)
continue;
drawAtt = &drawFb->Attachment[idx];
...
> +
> + /* If the source and destination are the same size with no
> + mirroring, the rectangles are within the size of the
> + texture and there is no scissor then we can use
> + glCopyTexSubimage2D to implement the blit. This will end
> + up as a fast hardware blit on some drivers */
> + if (srcRb && drawAtt && drawAtt->Texture &&
> + srcX0 - srcX1 == dstX0 - dstX1 &&
> + srcY0 - srcY1 == dstY0 - dstY1 &&
> + srcX1 >= srcX0 &&
> + srcY1 >= srcY0 &&
> + srcX0 >= 0 && srcX1 <= readFb->Width &&
> + srcY0 >= 0 && srcY1 <= readFb->Height &&
> + dstX0 >= 0 && dstX1 <= drawFb->Width &&
> + dstY0 >= 0 && dstY1 <= drawFb->Height &&
> + !ctx->Scissor.Enabled) {
> + const struct gl_texture_object *texObj = drawAtt->Texture;
> + const GLuint dstLevel = drawAtt->TextureLevel;
> + const GLenum target = texObj->Target;
> +
> + struct gl_texture_image *texImage =
> + _mesa_select_tex_image(ctx, texObj, target, dstLevel);
> +
> + result = intel_copy_texsubimage(intel_context(ctx),
> + intel_texture_image(texImage),
> + dstX0, dstY0,
> + srcRb,
> + srcX0, srcY0,
> + srcX1 - srcX0, /* width */
> + srcY1 - srcY0);
> + if (!result)
> + break;
> + }
> + /* This handles a case where not all the draw buffer attachments
> + * are textures.
> + */
> + else if (srcRb && drawAtt) {
> + result = false;
> + break;
> + }
> }
> +
> + if (result)
> + mask &= ~GL_COLOR_BUFFER_BIT;
> }
>
> return mask;
>
More information about the mesa-dev
mailing list