diff options
Diffstat (limited to 'mesalib/src/gallium/auxiliary/util/u_blitter.c')
-rw-r--r-- | mesalib/src/gallium/auxiliary/util/u_blitter.c | 134 |
1 files changed, 84 insertions, 50 deletions
diff --git a/mesalib/src/gallium/auxiliary/util/u_blitter.c b/mesalib/src/gallium/auxiliary/util/u_blitter.c index b31ac2d5c..fa71f25ea 100644 --- a/mesalib/src/gallium/auxiliary/util/u_blitter.c +++ b/mesalib/src/gallium/auxiliary/util/u_blitter.c @@ -439,6 +439,12 @@ static void blitter_restore_fragment_states(struct blitter_context_priv *ctx) pipe->bind_blend_state(pipe, ctx->base.saved_blend_state); ctx->base.saved_blend_state = INVALID_PTR; + /* Sample mask. */ + if (ctx->base.is_sample_mask_saved) { + pipe->set_sample_mask(pipe, ctx->base.saved_sample_mask); + ctx->base.is_sample_mask_saved = FALSE; + } + /* Miscellaneous states. */ /* XXX check whether these are saved and whether they need to be restored * (depending on the operation) */ @@ -848,6 +854,7 @@ static void util_blitter_clear_custom(struct blitter_context *blitter, pipe->bind_vertex_elements_state(pipe, ctx->velem_state); } pipe->bind_fs_state(pipe, blitter_get_fs_col(ctx, num_cbufs, int_format)); + pipe->set_sample_mask(pipe, ~0); blitter_set_common_draw_rect_state(ctx); blitter_set_dst_dimensions(ctx, width, height); @@ -925,66 +932,89 @@ void util_blitter_default_src_texture(struct pipe_sampler_view *src_templ, src_templ->swizzle_a = PIPE_SWIZZLE_ALPHA; } +boolean util_blitter_is_copy_supported(struct blitter_context *blitter, + const struct pipe_resource *dst, + const struct pipe_resource *src, + unsigned mask) +{ + struct blitter_context_priv *ctx = (struct blitter_context_priv*)blitter; + struct pipe_screen *screen = ctx->base.pipe->screen; + + if (dst) { + unsigned bind; + boolean is_stencil; + const struct util_format_description *desc = + util_format_description(dst->format); + + is_stencil = util_format_has_stencil(desc); + + /* Stencil export must be supported for stencil copy. */ + if ((mask & PIPE_MASK_S) && is_stencil && !ctx->has_stencil_export) { + return FALSE; + } + + if (is_stencil || util_format_has_depth(desc)) + bind = PIPE_BIND_DEPTH_STENCIL; + else + bind = PIPE_BIND_RENDER_TARGET; + + if (!screen->is_format_supported(screen, dst->format, dst->target, + dst->nr_samples, bind)) { + return FALSE; + } + } + + if (src) { + if (!screen->is_format_supported(screen, src->format, src->target, + src->nr_samples, PIPE_BIND_SAMPLER_VIEW)) { + return FALSE; + } + + /* Check stencil sampler support for stencil copy. */ + if (util_format_has_stencil(util_format_description(src->format))) { + enum pipe_format stencil_format = + util_format_stencil_only(src->format); + assert(stencil_format != PIPE_FORMAT_NONE); + + if (stencil_format != src->format && + !screen->is_format_supported(screen, stencil_format, src->target, + src->nr_samples, PIPE_BIND_SAMPLER_VIEW)) { + return FALSE; + } + } + } + + return TRUE; +} + void util_blitter_copy_texture(struct blitter_context *blitter, struct pipe_resource *dst, - unsigned dstlevel, + unsigned dst_level, unsigned dstx, unsigned dsty, unsigned dstz, struct pipe_resource *src, - unsigned srclevel, - const struct pipe_box *srcbox, - boolean ignore_stencil) + unsigned src_level, + const struct pipe_box *srcbox) { struct blitter_context_priv *ctx = (struct blitter_context_priv*)blitter; struct pipe_context *pipe = ctx->base.pipe; - struct pipe_screen *screen = pipe->screen; struct pipe_surface *dst_view, dst_templ; struct pipe_sampler_view src_templ, *src_view; - unsigned bind; - boolean is_stencil, is_depth; - const struct util_format_description *src_desc = - util_format_description(src->format); - /* Give up if textures are not set. */ assert(dst && src); - if (!dst || !src) - return; - assert(src->target < PIPE_MAX_TEXTURE_TYPES); - /* Is this a ZS format? */ - is_depth = util_format_has_depth(src_desc); - is_stencil = util_format_has_stencil(src_desc); - - if (is_depth || is_stencil) - bind = PIPE_BIND_DEPTH_STENCIL; - else - bind = PIPE_BIND_RENDER_TARGET; - - /* Check if we can sample from and render to the surfaces. */ - /* (assuming copying a stencil buffer is not possible) */ - if ((!ignore_stencil && is_stencil && !ctx->has_stencil_export) || - !screen->is_format_supported(screen, dst->format, dst->target, - dst->nr_samples, bind) || - !screen->is_format_supported(screen, src->format, src->target, - src->nr_samples, PIPE_BIND_SAMPLER_VIEW)) { - blitter_set_running_flag(ctx); - util_resource_copy_region(pipe, dst, dstlevel, dstx, dsty, dstz, - src, srclevel, srcbox); - blitter_unset_running_flag(ctx); - return; - } - /* Initialize the surface. */ - util_blitter_default_dst_texture(&dst_templ, dst, dstlevel, dstz, srcbox); + util_blitter_default_dst_texture(&dst_templ, dst, dst_level, dstz, srcbox); dst_view = pipe->create_surface(pipe, dst, &dst_templ); /* Initialize the sampler view. */ - util_blitter_default_src_texture(&src_templ, src, srclevel); + util_blitter_default_src_texture(&src_templ, src, src_level); src_view = pipe->create_sampler_view(pipe, src, &src_templ); /* Copy. */ util_blitter_copy_texture_view(blitter, dst_view, dstx, dsty, src_view, - srcbox, src->width0, src->height0); + srcbox, src->width0, src->height0, + PIPE_MASK_RGBAZS); pipe_surface_reference(&dst_view, NULL); pipe_sampler_view_reference(&src_view, NULL); @@ -995,7 +1025,8 @@ void util_blitter_copy_texture_view(struct blitter_context *blitter, unsigned dstx, unsigned dsty, struct pipe_sampler_view *src, const struct pipe_box *srcbox, - unsigned src_width0, unsigned src_height0) + unsigned src_width0, unsigned src_height0, + unsigned mask) { struct blitter_context_priv *ctx = (struct blitter_context_priv*)blitter; struct pipe_context *pipe = ctx->base.pipe; @@ -1003,19 +1034,19 @@ void util_blitter_copy_texture_view(struct blitter_context *blitter, enum pipe_texture_target src_target = src->texture->target; unsigned width = srcbox->width; unsigned height = srcbox->height; - boolean is_stencil, is_depth; + boolean blit_stencil, blit_depth; const struct util_format_description *src_desc = util_format_description(src->format); - is_depth = util_format_has_depth(src_desc); - is_stencil = util_format_has_stencil(src_desc); + blit_depth = util_format_has_depth(src_desc) && (mask & PIPE_MASK_Z); + blit_stencil = util_format_has_stencil(src_desc) && (mask & PIPE_MASK_S); /* If you want a fallback for stencil copies, * use util_blitter_copy_texture. */ - if (is_stencil && !ctx->has_stencil_export) { - is_stencil = FALSE; + if (blit_stencil && !ctx->has_stencil_export) { + blit_stencil = FALSE; - if (!is_depth) + if (!blit_depth) return; } @@ -1039,15 +1070,15 @@ void util_blitter_copy_texture_view(struct blitter_context *blitter, fb_state.width = dst->width; fb_state.height = dst->height; - if (is_depth || is_stencil) { + if (blit_depth || blit_stencil) { pipe->bind_blend_state(pipe, ctx->blend_keep_color); - if (is_depth && is_stencil) { + if (blit_depth && blit_stencil) { pipe->bind_depth_stencil_alpha_state(pipe, ctx->dsa_write_depth_stencil); pipe->bind_fs_state(pipe, blitter_get_fs_texfetch_depthstencil(ctx, src_target)); - } else if (is_depth) { + } else if (blit_depth) { pipe->bind_depth_stencil_alpha_state(pipe, ctx->dsa_write_depth_keep_stencil); pipe->bind_fs_state(pipe, @@ -1072,7 +1103,7 @@ void util_blitter_copy_texture_view(struct blitter_context *blitter, fb_state.zsbuf = 0; } - if (is_depth && is_stencil) { + if (blit_depth && blit_stencil) { /* Setup two samplers, one for depth and the other one for stencil. */ struct pipe_sampler_view templ; struct pipe_sampler_view *views[2]; @@ -1096,6 +1127,7 @@ void util_blitter_copy_texture_view(struct blitter_context *blitter, pipe->bind_vertex_elements_state(pipe, ctx->velem_state); pipe->set_framebuffer_state(pipe, &fb_state); + pipe->set_sample_mask(pipe, ~0); blitter_set_common_draw_rect_state(ctx); blitter_set_dst_dimensions(ctx, dst->width, dst->height); @@ -1183,6 +1215,7 @@ void util_blitter_clear_render_target(struct blitter_context *blitter, fb_state.cbufs[0] = dstsurf; fb_state.zsbuf = 0; pipe->set_framebuffer_state(pipe, &fb_state); + pipe->set_sample_mask(pipe, ~0); blitter_set_common_draw_rect_state(ctx); blitter_set_dst_dimensions(ctx, dstsurf->width, dstsurf->height); @@ -1248,6 +1281,7 @@ void util_blitter_clear_depth_stencil(struct blitter_context *blitter, fb_state.cbufs[0] = 0; fb_state.zsbuf = dstsurf; pipe->set_framebuffer_state(pipe, &fb_state); + pipe->set_sample_mask(pipe, ~0); blitter_set_common_draw_rect_state(ctx); blitter_set_dst_dimensions(ctx, dstsurf->width, dstsurf->height); |