summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/gallium/drivers/r600/r600_blit.c28
-rw-r--r--src/gallium/drivers/r600/r600_pipe.h2
-rw-r--r--src/gallium/drivers/r600/r600_resource.h1
-rw-r--r--src/gallium/drivers/r600/r600_state_common.c8
-rw-r--r--src/gallium/drivers/r600/r600_texture.c7
5 files changed, 42 insertions, 4 deletions
diff --git a/src/gallium/drivers/r600/r600_blit.c b/src/gallium/drivers/r600/r600_blit.c
index 71a504cb9a..83c02e5580 100644
--- a/src/gallium/drivers/r600/r600_blit.c
+++ b/src/gallium/drivers/r600/r600_blit.c
@@ -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)
{
diff --git a/src/gallium/drivers/r600/r600_pipe.h b/src/gallium/drivers/r600/r600_pipe.h
index cf4211cb8d..beb4db12b0 100644
--- a/src/gallium/drivers/r600/r600_pipe.h
+++ b/src/gallium/drivers/r600/r600_pipe.h
@@ -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,
diff --git a/src/gallium/drivers/r600/r600_resource.h b/src/gallium/drivers/r600/r600_resource.h
index 6e30244471..5b5df5a5ba 100644
--- a/src/gallium/drivers/r600/r600_resource.h
+++ b/src/gallium/drivers/r600/r600_resource.h
@@ -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
diff --git a/src/gallium/drivers/r600/r600_state_common.c b/src/gallium/drivers/r600/r600_state_common.c
index 2df8188f0a..e086e272c8 100644
--- a/src/gallium/drivers/r600/r600_state_common.c
+++ b/src/gallium/drivers/r600/r600_state_common.c
@@ -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 */
diff --git a/src/gallium/drivers/r600/r600_texture.c b/src/gallium/drivers/r600/r600_texture.c
index 51560bd19e..91076269ec 100644
--- a/src/gallium/drivers/r600/r600_texture.c
+++ b/src/gallium/drivers/r600/r600_texture.c
@@ -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);
}