diff options
author | Connor Abbott <cwabbott0@gmail.com> | 2021-04-23 13:05:48 +0200 |
---|---|---|
committer | Emma Anholt <emma@anholt.net> | 2021-06-10 12:24:06 -0700 |
commit | ba8efeb7fa4a8a1f9b917b6f5ac7df8c2aace52e (patch) | |
tree | 43da31a7a5f434ffc4b88a02f6da8f711ad6835b /src/freedreno | |
parent | 8b15c2f30c40155a56a211c2e1c1b6c5fc0368b9 (diff) |
ir3/sched: Make collects count against tex/sfu limits
In a scenario where there are a lot of texture fetches with constant
coordinates, this prevents the scheduler from scheduling all the setup
instructions after the first group of textures has been scheduled
because they are the only non-syncing thing and scheduling them didn't
decrease tex_delay. Collects with immed/const sources will turn into
moves of those sources, so we should treat them the same.
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/9842>
Diffstat (limited to 'src/freedreno')
-rw-r--r-- | src/freedreno/ir3/ir3_sched.c | 31 |
1 files changed, 25 insertions, 6 deletions
diff --git a/src/freedreno/ir3/ir3_sched.c b/src/freedreno/ir3/ir3_sched.c index 2e1cabfcd41..a51399e477d 100644 --- a/src/freedreno/ir3/ir3_sched.c +++ b/src/freedreno/ir3/ir3_sched.c @@ -220,6 +220,24 @@ is_outstanding_sfu(struct ir3_instruction *instr, struct ir3_sched_ctx *ctx) return n->sfu_index >= ctx->first_outstanding_sfu_index; } +static unsigned +cycle_count(struct ir3_instruction *instr) +{ + if (instr->opc == OPC_META_COLLECT) { + /* Assume that only immed/const sources produce moves */ + unsigned n = 0; + foreach_src(src, instr) { + if (src->flags & (IR3_REG_IMMED | IR3_REG_CONST)) + n++; + } + return n; + } else if (is_meta(instr)) { + return 0; + } else { + return 1; + } +} + static void schedule(struct ir3_sched_ctx *ctx, struct ir3_instruction *instr) { @@ -272,17 +290,17 @@ schedule(struct ir3_sched_ctx *ctx, struct ir3_instruction *instr) dag_prune_head(ctx->dag, &n->dag); - if (is_meta(instr) && (instr->opc != OPC_META_TEX_PREFETCH)) - return; + unsigned cycles = cycle_count(instr); if (is_sfu(instr)) { ctx->sfu_delay = 8; n->sfu_index = ctx->sfu_index++; - } else if (sched_check_src_cond(instr, is_outstanding_sfu, ctx)) { + } else if (!is_meta(instr) && + sched_check_src_cond(instr, is_outstanding_sfu, ctx)) { ctx->sfu_delay = 0; ctx->first_outstanding_sfu_index = ctx->sfu_index; } else if (ctx->sfu_delay > 0) { - ctx->sfu_delay--; + ctx->sfu_delay -= MIN2(cycles, ctx->sfu_delay); } if (is_tex_or_prefetch(instr)) { @@ -295,11 +313,12 @@ schedule(struct ir3_sched_ctx *ctx, struct ir3_instruction *instr) assert(ctx->remaining_tex > 0); ctx->remaining_tex--; n->tex_index = ctx->tex_index++; - } else if (sched_check_src_cond(instr, is_outstanding_tex_or_prefetch, ctx)) { + } else if (!is_meta(instr) && + sched_check_src_cond(instr, is_outstanding_tex_or_prefetch, ctx)) { ctx->tex_delay = 0; ctx->first_outstanding_tex_index = ctx->tex_index; } else if (ctx->tex_delay > 0) { - ctx->tex_delay--; + ctx->tex_delay -= MIN2(cycles, ctx->tex_delay); } } |