v3d: skip tlb loads when emitting clears with a draw call
We skip loading the tile buffer from memory if the job has flagged a clear (job->clears) for the buffer, however, this only tracks clears emitted via the TLB. In some cases we may need to fallback to clearing with a draw call, in which case we also want to skip the load. Reviewed-by: Jose Maria Casanova Crespo <jmcasanova@igalia.com> Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/30205>
This commit is contained in:

committed by
Marge Bot

parent
c9f26a9995
commit
4e19c139de
@@ -432,6 +432,11 @@ struct v3d_job {
|
|||||||
* first rendering.
|
* first rendering.
|
||||||
*/
|
*/
|
||||||
uint32_t clear;
|
uint32_t clear;
|
||||||
|
/* Bitmask of PIPE_CLEAR_* of buffers that were cleared using a draw
|
||||||
|
* call (not necessarily before the first rendering) instead of a TLB
|
||||||
|
* clear.
|
||||||
|
*/
|
||||||
|
uint32_t clear_draw;
|
||||||
/* Bitmask of PIPE_CLEAR_* of buffers that have been read by a draw
|
/* Bitmask of PIPE_CLEAR_* of buffers that have been read by a draw
|
||||||
* call without having been cleared first.
|
* call without having been cleared first.
|
||||||
*/
|
*/
|
||||||
|
@@ -1357,11 +1357,11 @@ v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info,
|
|||||||
u_stream_outputs_for_vertices(info->mode, draws[0].count);
|
u_stream_outputs_for_vertices(info->mode, draws[0].count);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
uint32_t clear_mask = job->clear | job->clear_draw;
|
||||||
if (v3d->zsa && job->zsbuf && v3d->zsa->base.depth_enabled) {
|
if (v3d->zsa && job->zsbuf && v3d->zsa->base.depth_enabled) {
|
||||||
struct v3d_resource *rsc = v3d_resource(job->zsbuf->texture);
|
struct v3d_resource *rsc = v3d_resource(job->zsbuf->texture);
|
||||||
v3d_job_add_bo(job, rsc->bo);
|
v3d_job_add_bo(job, rsc->bo);
|
||||||
|
job->load |= PIPE_CLEAR_DEPTH & ~clear_mask;
|
||||||
job->load |= PIPE_CLEAR_DEPTH & ~job->clear;
|
|
||||||
if (v3d->zsa->base.depth_writemask)
|
if (v3d->zsa->base.depth_writemask)
|
||||||
job->store |= PIPE_CLEAR_DEPTH;
|
job->store |= PIPE_CLEAR_DEPTH;
|
||||||
rsc->initialized_buffers = PIPE_CLEAR_DEPTH;
|
rsc->initialized_buffers = PIPE_CLEAR_DEPTH;
|
||||||
@@ -1374,7 +1374,7 @@ v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info,
|
|||||||
|
|
||||||
v3d_job_add_bo(job, rsc->bo);
|
v3d_job_add_bo(job, rsc->bo);
|
||||||
|
|
||||||
job->load |= PIPE_CLEAR_STENCIL & ~job->clear;
|
job->load |= PIPE_CLEAR_STENCIL & ~clear_mask;
|
||||||
if (v3d->zsa->base.stencil[0].writemask ||
|
if (v3d->zsa->base.stencil[0].writemask ||
|
||||||
v3d->zsa->base.stencil[1].writemask) {
|
v3d->zsa->base.stencil[1].writemask) {
|
||||||
job->store |= PIPE_CLEAR_STENCIL;
|
job->store |= PIPE_CLEAR_STENCIL;
|
||||||
@@ -1390,7 +1390,7 @@ v3d_draw_vbo(struct pipe_context *pctx, const struct pipe_draw_info *info,
|
|||||||
continue;
|
continue;
|
||||||
struct v3d_resource *rsc = v3d_resource(job->cbufs[i]->texture);
|
struct v3d_resource *rsc = v3d_resource(job->cbufs[i]->texture);
|
||||||
|
|
||||||
job->load |= bit & ~job->clear;
|
job->load |= bit & ~clear_mask;
|
||||||
if (v3d->blend->base.rt[blend_rt].colormask)
|
if (v3d->blend->base.rt[blend_rt].colormask)
|
||||||
job->store |= bit;
|
job->store |= bit;
|
||||||
v3d_job_add_bo(job, rsc->bo);
|
v3d_job_add_bo(job, rsc->bo);
|
||||||
@@ -1619,10 +1619,18 @@ v3d_launch_grid(struct pipe_context *pctx, const struct pipe_grid_info *info)
|
|||||||
*/
|
*/
|
||||||
static void
|
static void
|
||||||
v3d_draw_clear(struct v3d_context *v3d,
|
v3d_draw_clear(struct v3d_context *v3d,
|
||||||
|
struct v3d_job *job,
|
||||||
unsigned buffers,
|
unsigned buffers,
|
||||||
const union pipe_color_union *color,
|
const union pipe_color_union *color,
|
||||||
double depth, unsigned stencil)
|
double depth, unsigned stencil)
|
||||||
{
|
{
|
||||||
|
/* Flag we are clearing these buffers with a draw call so we can
|
||||||
|
* skip loads for them. Notice that if we had emitted any draw calls
|
||||||
|
* before this clear the loads will still happen, since those previous
|
||||||
|
* draw calls would have flagged them.
|
||||||
|
*/
|
||||||
|
job->clear_draw |= buffers;
|
||||||
|
|
||||||
v3d_blitter_save(v3d, false, true);
|
v3d_blitter_save(v3d, false, true);
|
||||||
util_blitter_clear(v3d->blitter,
|
util_blitter_clear(v3d->blitter,
|
||||||
v3d->framebuffer.width,
|
v3d->framebuffer.width,
|
||||||
@@ -1770,7 +1778,7 @@ v3d_clear(struct pipe_context *pctx, unsigned buffers, const struct pipe_scissor
|
|||||||
if (!buffers || !v3d_render_condition_check(v3d))
|
if (!buffers || !v3d_render_condition_check(v3d))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
v3d_draw_clear(v3d, buffers, color, depth, stencil);
|
v3d_draw_clear(v3d, job, buffers, color, depth, stencil);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
Reference in New Issue
Block a user