[Mesa-dev] [PATCH] u_blitter: Do blits in linear color space.
Marek Olšák
maraeo at gmail.com
Thu Mar 10 10:32:30 PST 2011
This looks good to me.
Marek
On Wed, Mar 9, 2011 at 9:31 PM, Henri Verbeet <hverbeet at gmail.com> wrote:
> Blits between sRGB and linear formats should happen in linear color space.
> This fixes piglit fbo/fbo-srgb-blit.
> ---
> src/gallium/auxiliary/util/u_blit.c | 57
> ++++++++++++++++++++------------
> src/gallium/auxiliary/util/u_blitter.c | 3 +-
> src/mesa/state_tracker/st_cb_texture.c | 2 +-
> 3 files changed, 39 insertions(+), 23 deletions(-)
>
> diff --git a/src/gallium/auxiliary/util/u_blit.c
> b/src/gallium/auxiliary/util/u_blit.c
> index 76bd7ac..3618353 100644
> --- a/src/gallium/auxiliary/util/u_blit.c
> +++ b/src/gallium/auxiliary/util/u_blit.c
> @@ -304,8 +304,10 @@ util_blit_pixels_writemask(struct blit_state *ctx,
> {
> struct pipe_context *pipe = ctx->pipe;
> struct pipe_screen *screen = pipe->screen;
> + enum pipe_format src_format, dst_format;
> struct pipe_sampler_view *sampler_view = NULL;
> struct pipe_sampler_view sv_templ;
> + struct pipe_surface *dst_surface;
> struct pipe_framebuffer_state fb;
> const int srcW = abs(srcX1 - srcX0);
> const int srcH = abs(srcY1 - srcY0);
> @@ -326,12 +328,15 @@ util_blit_pixels_writemask(struct blit_state *ctx,
> regions_overlap(srcX0, srcY0, srcX1, srcY1,
> dstX0, dstY0, dstX1, dstY1);
>
> + src_format = util_format_linear(src_tex->format);
> + dst_format = util_format_linear(dst->format);
> +
> /*
> * Check for simple case: no format conversion, no flipping, no
> stretching,
> * no overlapping.
> * Filter mode should not matter since there's no stretching.
> */
> - if (dst->format == src_tex->format &&
> + if (dst_format == src_format &&
> srcX0 < srcX1 &&
> dstX0 < dstX1 &&
> srcY0 < srcY1 &&
> @@ -354,6 +359,14 @@ util_blit_pixels_writemask(struct blit_state *ctx,
> return;
> }
>
> + if (dst_format == dst->format) {
> + dst_surface = dst;
> + } else {
> + struct pipe_surface templ = *dst;
> + templ.format = dst_format;
> + dst_surface = pipe->create_surface(pipe, dst->texture, &templ);
> + }
> +
> /* Create a temporary texture when src and dest alias or when src
> * is anything other than a 2d texture.
> * XXX should just use appropriate shader to access 1d / 3d slice / cube
> face,
> @@ -361,9 +374,9 @@ util_blit_pixels_writemask(struct blit_state *ctx,
> *
> * This can still be improved upon.
> */
> - if ((src_tex == dst->texture &&
> - dst->u.tex.level == src_level &&
> - dst->u.tex.first_layer == srcZ0) ||
> + if ((src_tex == dst_surface->texture &&
> + dst_surface->u.tex.level == src_level &&
> + dst_surface->u.tex.first_layer == srcZ0) ||
> (src_tex->target != PIPE_TEXTURE_2D &&
> src_tex->target != PIPE_TEXTURE_2D &&
> src_tex->target != PIPE_TEXTURE_RECT))
> @@ -392,7 +405,7 @@ util_blit_pixels_writemask(struct blit_state *ctx,
> /* create temp texture */
> memset(&texTemp, 0, sizeof(texTemp));
> texTemp.target = ctx->internal_target;
> - texTemp.format = src_tex->format;
> + texTemp.format = src_format;
> texTemp.last_level = 0;
> texTemp.width0 = srcW;
> texTemp.height0 = srcH;
> @@ -439,7 +452,7 @@ util_blit_pixels_writemask(struct blit_state *ctx,
> pipe_resource_reference(&tex, NULL);
> }
> else {
> - u_sampler_view_default_template(&sv_templ, src_tex,
> src_tex->format);
> + u_sampler_view_default_template(&sv_templ, src_tex, src_format);
> sampler_view = pipe->create_sampler_view(pipe, src_tex, &sv_templ);
>
> if (!sampler_view) {
> @@ -460,13 +473,13 @@ util_blit_pixels_writemask(struct blit_state *ctx,
> }
> }
>
> - dst_is_depth = util_format_is_depth_or_stencil(dst->format);
> + dst_is_depth = util_format_is_depth_or_stencil(dst_format);
>
> assert(screen->is_format_supported(screen, sampler_view->format,
> ctx->internal_target,
> sampler_view->texture->nr_samples,
> PIPE_BIND_SAMPLER_VIEW, 0));
> - assert(screen->is_format_supported(screen, dst->format,
> ctx->internal_target,
> - dst->texture->nr_samples,
> + assert(screen->is_format_supported(screen, dst_format,
> ctx->internal_target,
> + dst_surface->texture->nr_samples,
> dst_is_depth ?
> PIPE_BIND_DEPTH_STENCIL :
>
> PIPE_BIND_RENDER_TARGET, 0));
> /* save state (restored below) */
> @@ -502,12 +515,12 @@ util_blit_pixels_writemask(struct blit_state *ctx,
> cso_single_sampler_done(ctx->cso);
>
> /* viewport */
> - ctx->viewport.scale[0] = 0.5f * dst->width;
> - ctx->viewport.scale[1] = 0.5f * dst->height;
> + ctx->viewport.scale[0] = 0.5f * dst_surface->width;
> + ctx->viewport.scale[1] = 0.5f * dst_surface->height;
> ctx->viewport.scale[2] = 0.5f;
> ctx->viewport.scale[3] = 1.0f;
> - ctx->viewport.translate[0] = 0.5f * dst->width;
> - ctx->viewport.translate[1] = 0.5f * dst->height;
> + ctx->viewport.translate[0] = 0.5f * dst_surface->width;
> + ctx->viewport.translate[1] = 0.5f * dst_surface->height;
> ctx->viewport.translate[2] = 0.5f;
> ctx->viewport.translate[3] = 0.0f;
> cso_set_viewport(ctx->cso, &ctx->viewport);
> @@ -536,22 +549,22 @@ util_blit_pixels_writemask(struct blit_state *ctx,
>
> /* drawing dest */
> memset(&fb, 0, sizeof(fb));
> - fb.width = dst->width;
> - fb.height = dst->height;
> + fb.width = dst_surface->width;
> + fb.height = dst_surface->height;
> if (dst_is_depth) {
> - fb.zsbuf = dst;
> + fb.zsbuf = dst_surface;
> } else {
> fb.nr_cbufs = 1;
> - fb.cbufs[0] = dst;
> + fb.cbufs[0] = dst_surface;
> }
> cso_set_framebuffer(ctx->cso, &fb);
>
> /* draw quad */
> offset = setup_vertex_data_tex(ctx,
> - (float) dstX0 / dst->width * 2.0f -
> 1.0f,
> - (float) dstY0 / dst->height * 2.0f -
> 1.0f,
> - (float) dstX1 / dst->width * 2.0f -
> 1.0f,
> - (float) dstY1 / dst->height * 2.0f -
> 1.0f,
> + (float) dstX0 / dst_surface->width *
> 2.0f - 1.0f,
> + (float) dstY0 / dst_surface->height *
> 2.0f - 1.0f,
> + (float) dstX1 / dst_surface->width *
> 2.0f - 1.0f,
> + (float) dstY1 / dst_surface->height *
> 2.0f - 1.0f,
> s0, t0,
> s1, t1,
> z);
> @@ -576,6 +589,8 @@ util_blit_pixels_writemask(struct blit_state *ctx,
> cso_restore_vertex_buffers(ctx->cso);
>
> pipe_sampler_view_reference(&sampler_view, NULL);
> + if (dst_surface != dst)
> + pipe_surface_reference(&dst_surface, NULL);
> }
>
>
> diff --git a/src/gallium/auxiliary/util/u_blitter.c
> b/src/gallium/auxiliary/util/u_blitter.c
> index fd1c2b7..287f5da 100644
> --- a/src/gallium/auxiliary/util/u_blitter.c
> +++ b/src/gallium/auxiliary/util/u_blitter.c
> @@ -785,6 +785,7 @@ void util_blitter_copy_region(struct blitter_context
> *blitter,
> /* Get surface. */
> memset(&surf_templ, 0, sizeof(surf_templ));
> u_surface_default_template(&surf_templ, dst, bind);
> + surf_templ.format = util_format_linear(dst->format);
> surf_templ.u.tex.level = dstlevel;
> surf_templ.u.tex.first_layer = dstz;
> surf_templ.u.tex.last_layer = dstz;
> @@ -823,7 +824,7 @@ void util_blitter_copy_region(struct blitter_context
> *blitter,
> normalized = src->target != PIPE_TEXTURE_RECT;
>
> /* Initialize sampler view. */
> - u_sampler_view_default_template(&viewTempl, src, src->format);
> + u_sampler_view_default_template(&viewTempl, src,
> util_format_linear(src->format));
> view = pipe->create_sampler_view(pipe, src, &viewTempl);
>
> /* Set rasterizer state, shaders, and textures. */
> diff --git a/src/mesa/state_tracker/st_cb_texture.c
> b/src/mesa/state_tracker/st_cb_texture.c
> index 3f98ffd..ab2d645 100644
> --- a/src/mesa/state_tracker/st_cb_texture.c
> +++ b/src/mesa/state_tracker/st_cb_texture.c
> @@ -1533,7 +1533,7 @@ st_copy_texsubimage(struct gl_context *ctx,
> GLint srcY0, srcY1;
> struct pipe_surface surf_tmpl;
> memset(&surf_tmpl, 0, sizeof(surf_tmpl));
> - surf_tmpl.format = stImage->pt->format;
> + surf_tmpl.format = util_format_linear(stImage->pt->format);
> surf_tmpl.usage = PIPE_BIND_RENDER_TARGET;
> surf_tmpl.u.tex.level = stImage->level;
> surf_tmpl.u.tex.first_layer = stImage->face + destZ;
> --
> 1.7.2.3
>
> _______________________________________________
> 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/20110310/c2e59d2a/attachment.html>
More information about the mesa-dev
mailing list