aco: allow barriers to be skipped during scheduling

Much better scheduling apparently in 160 shaders

Totals from affected shaders:
SGPRS: 6272 -> 6344 (1.15 %)
VGPRS: 4832 -> 4844 (0.25 %)
Spilled SGPRs: 0 -> 0 (0.00 %)
Spilled VGPRs: 0 -> 0 (0.00 %)
Scratch size: 0 -> 0 (0.00 %) dwords per thread
Code Size: 467192 -> 467428 (0.05 %) bytes
LDS: 459 -> 459 (0.00 %) blocks
Max Waves: 1407 -> 1409 (0.14 %)
SMEM score: 9309.00 -> 11216.00 (20.49 %)
VMEM score: 26679.00 -> 33652.00 (26.14 %)
SMEM clauses: 1817 -> 1776 (-2.26 %)
VMEM clauses: 2286 -> 2288 (0.09 %)
Instructions: 86537 -> 86596 (0.07 %)
Cycles: 676260 -> 676568 (0.05 %)

Signed-off-by: Rhys Perry <pendingchaos02@gmail.com>
Reviewed-by: Daniel Schürmann <daniel@schuermann.dev>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/3776>
This commit is contained in:
Rhys Perry 2020-02-11 14:15:32 +00:00 committed by Marge Bot
parent 928ac97875
commit 6b4c31f814
1 changed files with 25 additions and 17 deletions

View File

@ -453,6 +453,7 @@ barrier_interaction parse_barrier(Instruction *instr)
struct hazard_query { struct hazard_query {
bool contains_spill; bool contains_spill;
int barriers; int barriers;
int barrier_interaction;
bool can_reorder_vmem; bool can_reorder_vmem;
bool can_reorder_smem; bool can_reorder_smem;
}; };
@ -460,13 +461,15 @@ struct hazard_query {
void init_hazard_query(hazard_query *query) { void init_hazard_query(hazard_query *query) {
query->contains_spill = false; query->contains_spill = false;
query->barriers = 0; query->barriers = 0;
query->barrier_interaction = 0;
query->can_reorder_vmem = true; query->can_reorder_vmem = true;
query->can_reorder_smem = true; query->can_reorder_smem = true;
} }
void add_to_hazard_query(hazard_query *query, Instruction *instr) void add_to_hazard_query(hazard_query *query, Instruction *instr)
{ {
query->barriers |= get_barrier_interaction(instr); query->barriers |= parse_barrier(instr);
query->barrier_interaction |= get_barrier_interaction(instr);
if (instr->opcode == aco_opcode::p_spill || instr->opcode == aco_opcode::p_reload) if (instr->opcode == aco_opcode::p_spill || instr->opcode == aco_opcode::p_reload)
query->contains_spill = true; query->contains_spill = true;
@ -481,10 +484,12 @@ enum HazardResult {
hazard_fail_reorder_ds, hazard_fail_reorder_ds,
hazard_fail_reorder_sendmsg, hazard_fail_reorder_sendmsg,
hazard_fail_spill, hazard_fail_spill,
hazard_fail_export,
hazard_fail_barrier,
/* Must stop at these failures. The hazard query code doesn't consider them /* Must stop at these failures. The hazard query code doesn't consider them
* when added. */ * when added. */
hazard_fail_exec, hazard_fail_exec,
hazard_fail_barrier, hazard_fail_memtime,
}; };
HazardResult perform_hazard_query(hazard_query *query, Instruction *instr) HazardResult perform_hazard_query(hazard_query *query, Instruction *instr)
@ -500,22 +505,24 @@ HazardResult perform_hazard_query(hazard_query *query, Instruction *instr)
/* don't move exports so that they stay closer together */ /* don't move exports so that they stay closer together */
if (instr->format == Format::EXP) if (instr->format == Format::EXP)
return hazard_fail_barrier; return hazard_fail_export;
/* don't move s_memtime/s_memrealtime */ /* don't move s_memtime/s_memrealtime */
if (instr->opcode == aco_opcode::s_memtime || instr->opcode == aco_opcode::s_memrealtime) if (instr->opcode == aco_opcode::s_memtime || instr->opcode == aco_opcode::s_memrealtime)
return hazard_fail_barrier; return hazard_fail_memtime;
if (query->barriers & parse_barrier(instr)) if (query->barrier_interaction && (query->barrier_interaction & parse_barrier(instr)))
return hazard_fail_barrier;
if (query->barriers && (query->barriers & get_barrier_interaction(instr)))
return hazard_fail_barrier; return hazard_fail_barrier;
if (!query->can_reorder_smem && instr->format == Format::SMEM && !can_reorder_candidate) if (!query->can_reorder_smem && instr->format == Format::SMEM && !can_reorder_candidate)
return hazard_fail_reorder_vmem_smem; return hazard_fail_reorder_vmem_smem;
if (!query->can_reorder_vmem && (instr->isVMEM() || instr->isFlatOrGlobal()) && !can_reorder_candidate) if (!query->can_reorder_vmem && (instr->isVMEM() || instr->isFlatOrGlobal()) && !can_reorder_candidate)
return hazard_fail_reorder_vmem_smem; return hazard_fail_reorder_vmem_smem;
if ((query->barriers & barrier_shared) && instr->format == Format::DS) if ((query->barrier_interaction & barrier_shared) && instr->format == Format::DS)
return hazard_fail_reorder_ds; return hazard_fail_reorder_ds;
if (is_gs_or_done_sendmsg(instr) && (query->barriers & get_barrier_interaction(instr))) if (is_gs_or_done_sendmsg(instr) && (query->barrier_interaction & get_barrier_interaction(instr)))
return hazard_fail_reorder_sendmsg; return hazard_fail_reorder_sendmsg;
if ((instr->opcode == aco_opcode::p_spill || instr->opcode == aco_opcode::p_reload) && if ((instr->opcode == aco_opcode::p_spill || instr->opcode == aco_opcode::p_reload) &&
@ -564,10 +571,9 @@ void schedule_SMEM(sched_ctx& ctx, Block* block,
bool can_move_down = true; bool can_move_down = true;
HazardResult haz = perform_hazard_query(&hq, candidate.get()); HazardResult haz = perform_hazard_query(&hq, candidate.get());
if (haz == hazard_fail_reorder_ds || haz == hazard_fail_spill || haz == hazard_fail_reorder_sendmsg) if (haz == hazard_fail_reorder_ds || haz == hazard_fail_spill || haz == hazard_fail_reorder_sendmsg || haz == hazard_fail_barrier)
can_move_down = false; can_move_down = false;
else if (haz == hazard_fail_reorder_vmem_smem || haz == hazard_fail_barrier || else if (haz != hazard_success)
haz == hazard_fail_exec)
break; break;
/* don't use LDS/GDS instructions to hide latency since it can /* don't use LDS/GDS instructions to hide latency since it can
@ -613,10 +619,10 @@ void schedule_SMEM(sched_ctx& ctx, Block* block,
if (found_dependency) { if (found_dependency) {
HazardResult haz = perform_hazard_query(&hq, candidate.get()); HazardResult haz = perform_hazard_query(&hq, candidate.get());
if (haz == hazard_fail_reorder_ds || haz == hazard_fail_spill || haz == hazard_fail_reorder_sendmsg) if (haz == hazard_fail_reorder_ds || haz == hazard_fail_spill ||
haz == hazard_fail_reorder_sendmsg || haz == hazard_fail_barrier)
is_dependency = true; is_dependency = true;
else if (haz == hazard_fail_reorder_vmem_smem || haz == hazard_fail_barrier || else if (haz != hazard_success)
haz == hazard_fail_exec)
break; break;
} }
@ -704,7 +710,8 @@ void schedule_VMEM(sched_ctx& ctx, Block* block,
bool can_move_down = !is_vmem || part_of_clause; bool can_move_down = !is_vmem || part_of_clause;
HazardResult haz = perform_hazard_query(part_of_clause ? &clause_hq : &indep_hq, candidate.get()); HazardResult haz = perform_hazard_query(part_of_clause ? &clause_hq : &indep_hq, candidate.get());
if (haz == hazard_fail_reorder_ds || haz == hazard_fail_spill || haz == hazard_fail_reorder_sendmsg) if (haz == hazard_fail_reorder_ds || haz == hazard_fail_spill ||
haz == hazard_fail_reorder_sendmsg || haz == hazard_fail_barrier)
can_move_down = false; can_move_down = false;
else if (haz != hazard_success) else if (haz != hazard_success)
break; break;
@ -749,9 +756,10 @@ void schedule_VMEM(sched_ctx& ctx, Block* block,
if (found_dependency) { if (found_dependency) {
HazardResult haz = perform_hazard_query(&indep_hq, candidate.get()); HazardResult haz = perform_hazard_query(&indep_hq, candidate.get());
if (haz == hazard_fail_reorder_ds || haz == hazard_fail_spill || if (haz == hazard_fail_reorder_ds || haz == hazard_fail_spill ||
haz == hazard_fail_reorder_vmem_smem || haz == hazard_fail_reorder_sendmsg) haz == hazard_fail_reorder_vmem_smem || haz == hazard_fail_reorder_sendmsg ||
haz == hazard_fail_barrier)
is_dependency = true; is_dependency = true;
else if (haz == hazard_fail_barrier || haz == hazard_fail_exec) else if (haz != hazard_success)
break; break;
} }
@ -814,7 +822,7 @@ void schedule_position_export(sched_ctx& ctx, Block* block,
break; break;
HazardResult haz = perform_hazard_query(&hq, candidate.get()); HazardResult haz = perform_hazard_query(&hq, candidate.get());
if (haz == hazard_fail_barrier || haz == hazard_fail_exec) if (haz == hazard_fail_exec || haz == hazard_fail_export || haz == hazard_fail_memtime)
break; break;
if (haz != hazard_success) { if (haz != hazard_success) {