r600g: Update the flushed depth texture after drawing to the corresponding texture.
authorHenri Verbeet <hverbeet@gmail.com>
Sun, 30 Jan 2011 17:57:39 +0000 (18:57 +0100)
committerHenri Verbeet <hverbeet@gmail.com>
Sun, 30 Jan 2011 17:59:13 +0000 (18:59 +0100)
I know Jerome will probably rewrite the way depth textures work sometime
soon. For the time being this should at least make common depth texture usage
for shadowing work properly though.

src/gallium/drivers/r600/r600_blit.c
src/gallium/drivers/r600/r600_pipe.h
src/gallium/drivers/r600/r600_resource.h
src/gallium/drivers/r600/r600_state_common.c
src/gallium/drivers/r600/r600_texture.c

index 71a504cb9a23a1748d9aa5b6cf16aab12ce0d8cb..83c02e55802ff6111250c0fc625fd71e7daaf79f 100644 (file)
@@ -36,6 +36,7 @@ static void r600_blitter_begin(struct pipe_context *ctx, enum r600_blitter_op op
 {
        struct r600_pipe_context *rctx = (struct r600_pipe_context *)ctx;
 
+       rctx->blit = true;
        r600_context_queries_suspend(&rctx->ctx);
 
        util_blitter_save_blend(rctx->blitter, rctx->states[R600_PIPE_STATE_BLEND]);
@@ -74,6 +75,7 @@ static void r600_blitter_end(struct pipe_context *ctx)
 {
        struct r600_pipe_context *rctx = (struct r600_pipe_context *)ctx;
        r600_context_queries_resume(&rctx->ctx);
+       rctx->blit = false;
 }
 
 void r600_blit_uncompress_depth(struct pipe_context *ctx, struct r600_resource_texture *texture)
@@ -82,6 +84,9 @@ void r600_blit_uncompress_depth(struct pipe_context *ctx, struct r600_resource_t
        struct pipe_surface *zsurf, *cbsurf, surf_tmpl;
        int level = 0;
        float depth = 1.0f;
+
+       if (texture->flushed) return;
+
        surf_tmpl.format = texture->resource.base.b.format;
        surf_tmpl.u.tex.level = level;
        surf_tmpl.u.tex.first_layer = 0;
@@ -102,11 +107,34 @@ void r600_blit_uncompress_depth(struct pipe_context *ctx, struct r600_resource_t
        r600_blitter_begin(ctx, R600_CLEAR_SURFACE);
        util_blitter_custom_depth_stencil(rctx->blitter, zsurf, cbsurf, rctx->custom_dsa_flush, depth);
        r600_blitter_end(ctx);
+       texture->flushed = true;
 
        pipe_surface_reference(&zsurf, NULL);
        pipe_surface_reference(&cbsurf, NULL);
 }
 
+void r600_flush_depth_textures(struct r600_pipe_context *rctx)
+{
+       unsigned int i;
+
+       if (rctx->blit) return;
+
+       /* FIXME: This handles fragment shader textures only. */
+
+       for (i = 0; i < rctx->ps_samplers.n_views; ++i) {
+               struct r600_pipe_sampler_view *view;
+               struct r600_resource_texture *tex;
+
+               view = rctx->ps_samplers.views[i];
+               if (!view) continue;
+
+               tex = (struct r600_resource_texture *)view->base.texture;
+               if (!tex->depth) continue;
+
+               r600_blit_uncompress_depth(&rctx->context, tex);
+       }
+}
+
 static void r600_clear(struct pipe_context *ctx, unsigned buffers,
                        const float *rgba, double depth, unsigned stencil)
 {
index cf4211cb8d3bb51a6e2c948d30ff72c8aee56bcb..beb4db12b08069eab6adab00a990b2659e690b52 100644 (file)
@@ -171,6 +171,7 @@ struct r600_pipe_context {
        unsigned                        vb_max_index;
        struct r600_translate_context   tran;
        struct u_upload_mgr             *upload_const;
+       bool                            blit;
 };
 
 struct r600_drawl {
@@ -197,6 +198,7 @@ void evergreen_pipe_add_vertex_attrib(struct r600_pipe_context *rctx,
 /* r600_blit.c */
 void r600_init_blit_functions(struct r600_pipe_context *rctx);
 void r600_blit_uncompress_depth(struct pipe_context *ctx, struct r600_resource_texture *texture);
+void r600_flush_depth_textures(struct r600_pipe_context *rctx);
 
 /* r600_buffer.c */
 struct pipe_resource *r600_buffer_create(struct pipe_screen *screen,
index 6e302444712677fa835133e11763ffefa15c88a1..5b5df5a5bac3592479fc6e738949ce8f6a028cfc 100644 (file)
@@ -63,6 +63,7 @@ struct r600_resource_texture {
        unsigned                        depth;
        unsigned                        dirty;
        struct r600_resource_texture    *flushed_depth_texture;
+       bool                            flushed;
 };
 
 #define R600_BUFFER_MAGIC 0xabcd1600
index 2df8188f0a2334c97245c9149b683149cba097e2..e086e272c8e2f5817d95b025dfdeb0a1cbd8c578 100644 (file)
@@ -496,6 +496,8 @@ void r600_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
        struct r600_drawl draw = {};
        unsigned prim;
 
+       r600_flush_depth_textures(rctx);
+
        if (rctx->vertex_elements->incompatible_layout) {
                r600_begin_vertex_translate(rctx, info->min_index, info->max_index);
        }
@@ -597,6 +599,12 @@ void r600_draw_vbo(struct pipe_context *ctx, const struct pipe_draw_info *info)
                r600_context_draw(&rctx->ctx, &rdraw);
        }
 
+       if (rctx->framebuffer.zsbuf)
+       {
+               struct pipe_resource *tex = rctx->framebuffer.zsbuf->texture;
+               ((struct r600_resource_texture *)tex)->flushed = false;
+       }
+
        pipe_resource_reference(&draw.index_buffer, NULL);
 
        /* delete previous translated vertex elements */
index 51560bd19e60753b029785cecf1e73711bf23a65..91076269ec7f6a8acf78038c49501aed38b37c90 100644 (file)
@@ -302,6 +302,9 @@ r600_texture_create_object(struct pipe_screen *screen,
        resource->bo = bo;
        rtex->pitch_override = pitch_in_bytes_override;
 
+       if (util_format_is_depth_or_stencil(base->format))
+               rtex->depth = 1;
+
        if (array_mode)
                rtex->tiled = 1;
        r600_setup_miptree(screen, rtex, array_mode);
@@ -632,7 +635,6 @@ void r600_texture_transfer_destroy(struct pipe_context *ctx,
                                   struct pipe_transfer *transfer)
 {
        struct r600_transfer *rtransfer = (struct r600_transfer*)transfer;
-       struct r600_resource_texture *rtex = (struct r600_resource_texture*)transfer->resource;
 
        if (rtransfer->staging_texture) {
                if (transfer->usage & PIPE_TRANSFER_WRITE) {
@@ -640,9 +642,6 @@ void r600_texture_transfer_destroy(struct pipe_context *ctx,
                }
                pipe_resource_reference(&rtransfer->staging_texture, NULL);
        }
-       if (rtex->flushed_depth_texture) {
-               pipe_resource_reference((struct pipe_resource **)&rtex->flushed_depth_texture, NULL);
-       }
        pipe_resource_reference(&transfer->resource, NULL);
        FREE(transfer);
 }