freedreno: handle invalidated buffers harder

Do a better job of skipping mem2gmem/gmem2mem..

Signed-off-by: Rob Clark <robdclark@gmail.com>
This commit is contained in:
Rob Clark 2018-09-11 16:21:29 -04:00
parent 19e9d28646
commit 919741b8d5
8 changed files with 39 additions and 7 deletions

View File

@ -69,6 +69,9 @@ emit_gmem2mem_surf(struct fd_batch *batch, uint32_t base,
struct fd_resource *rsc = fd_resource(psurf->texture);
uint32_t swap = fmt2swap(psurf->format);
if (!rsc->valid)
return;
OUT_PKT3(ring, CP_SET_CONSTANT, 2);
OUT_RING(ring, CP_REG(REG_A2XX_RB_COLOR_INFO));
OUT_RING(ring, A2XX_RB_COLOR_INFO_SWAP(swap) |

View File

@ -322,10 +322,15 @@ emit_gmem2mem_surf(struct fd_batch *batch,
struct fd_ringbuffer *ring = batch->gmem;
struct fd_resource *rsc = fd_resource(psurf->texture);
enum pipe_format format = psurf->format;
if (!rsc->valid)
return;
if (stencil) {
rsc = rsc->stencil;
format = rsc->base.format;
}
struct fd_resource_slice *slice = fd_resource_slice(rsc, psurf->u.tex.level);
uint32_t offset = fd_resource_offset(rsc, psurf->u.tex.level,
psurf->u.tex.first_layer);

View File

@ -157,6 +157,9 @@ emit_gmem2mem_surf(struct fd_batch *batch, bool stencil,
struct fd_resource_slice *slice;
uint32_t offset;
if (!rsc->valid)
return;
if (stencil) {
debug_assert(rsc->stencil);
rsc = rsc->stencil;

View File

@ -614,6 +614,9 @@ emit_gmem2mem_surf(struct fd_batch *batch, uint32_t base,
bool tiled;
uint32_t offset;
if (!rsc->valid)
return;
if (buf == BLIT_S)
rsc = rsc->stencil;

View File

@ -681,6 +681,9 @@ emit_resolve_blit(struct fd_batch *batch, uint32_t base,
struct fd_ringbuffer *ring = batch->gmem;
uint32_t info = 0;
if (!rsc->valid)
return;
switch (buffer) {
case FD_BUFFER_COLOR:
break;

View File

@ -70,6 +70,7 @@ batch_init(struct fd_batch *batch)
batch->fence = fd_fence_create(batch);
batch->cleared = 0;
batch->invalidated = 0;
batch->restore = batch->resolve = 0;
batch->needs_flush = false;
batch->flushed = false;

View File

@ -84,6 +84,10 @@ struct fd_batch {
* The 'cleared' bits will be set for buffers which are *entirely*
* cleared, and 'partial_cleared' bits will be set if you must
* check cleared_scissor.
*
* The 'invalidated' bits are set for cleared buffers, and buffers
* where the contents are undefined, ie. what we don't need to restore
* to gmem.
*/
enum {
/* align bitmask values w/ PIPE_CLEAR_*.. since that is convenient.. */
@ -91,7 +95,7 @@ struct fd_batch {
FD_BUFFER_DEPTH = PIPE_CLEAR_DEPTH,
FD_BUFFER_STENCIL = PIPE_CLEAR_STENCIL,
FD_BUFFER_ALL = FD_BUFFER_COLOR | FD_BUFFER_DEPTH | FD_BUFFER_STENCIL,
} cleared, restore, resolve;
} invalidated, cleared, restore, resolve;
/* is this a non-draw batch (ie compute/blit which has no pfb state)? */
bool nondraw : 1;

View File

@ -137,16 +137,22 @@ fd_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
mtx_lock(&ctx->screen->lock);
if (fd_depth_enabled(ctx)) {
if (fd_resource(pfb->zsbuf->texture)->valid)
if (fd_resource(pfb->zsbuf->texture)->valid) {
restore_buffers |= FD_BUFFER_DEPTH;
} else {
batch->invalidated |= FD_BUFFER_DEPTH;
}
buffers |= FD_BUFFER_DEPTH;
resource_written(batch, pfb->zsbuf->texture);
batch->gmem_reason |= FD_GMEM_DEPTH_ENABLED;
}
if (fd_stencil_enabled(ctx)) {
if (fd_resource(pfb->zsbuf->texture)->valid)
if (fd_resource(pfb->zsbuf->texture)->valid) {
restore_buffers |= FD_BUFFER_STENCIL;
} else {
batch->invalidated |= FD_BUFFER_STENCIL;
}
buffers |= FD_BUFFER_STENCIL;
resource_written(batch, pfb->zsbuf->texture);
batch->gmem_reason |= FD_GMEM_STENCIL_ENABLED;
@ -163,10 +169,13 @@ fd_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
surf = pfb->cbufs[i]->texture;
resource_written(batch, surf);
if (fd_resource(surf)->valid)
if (fd_resource(surf)->valid) {
restore_buffers |= PIPE_CLEAR_COLOR0 << i;
} else {
batch->invalidated |= PIPE_CLEAR_COLOR0 << i;
}
resource_written(batch, surf);
buffers |= PIPE_CLEAR_COLOR0 << i;
@ -242,7 +251,7 @@ fd_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info)
ctx->stats.prims_generated += prims;
/* any buffers that haven't been cleared yet, we need to restore: */
batch->restore |= restore_buffers & (FD_BUFFER_ALL & ~batch->cleared);
batch->restore |= restore_buffers & (FD_BUFFER_ALL & ~batch->invalidated);
/* and any buffers used, need to be resolved: */
batch->resolve |= buffers;
@ -372,6 +381,7 @@ fd_clear(struct pipe_context *pctx, unsigned buffers,
*/
cleared_buffers = buffers & (FD_BUFFER_ALL & ~batch->restore);
batch->cleared |= cleared_buffers;
batch->invalidated |= cleared_buffers;
batch->resolve |= buffers;
batch->needs_flush = true;