ac/llvm: fix demote inside conditional branches

The big comment explains it.

v2: don't kill if subgroup ops are used

Reviewed-by: Rhys Perry <pendingchaos02@gmail.com>
Part-of: <https://gitlab.freedesktop.org/mesa/mesa/-/merge_requests/7586>
This commit is contained in:
Marek Olšák
2020-09-20 22:50:52 -04:00
committed by Marge Bot
parent cb20d58f45
commit aa757f4f8c
3 changed files with 47 additions and 4 deletions

View File

@@ -3138,6 +3138,22 @@ void ac_build_else(struct ac_llvm_context *ctx, int label_id)
current_branch->next_block = endif_block;
}
/* Invoked after a branch is exited. */
static void ac_branch_exited(struct ac_llvm_context *ctx)
{
if (ctx->flow->depth == 0 && ctx->conditional_demote_seen) {
/* The previous conditional branch contained demote. Kill threads
* after all conditional blocks because amdgcn.wqm.vote doesn't
* return usable values inside the blocks.
*
* This is an optional optimization that only kills whole inactive quads.
*/
LLVMValueRef cond = LLVMBuildLoad(ctx->builder, ctx->postponed_kill, "");
ac_build_kill_if_false(ctx, ac_build_wqm_vote(ctx, cond));
ctx->conditional_demote_seen = false;
}
}
void ac_build_endif(struct ac_llvm_context *ctx, int label_id)
{
struct ac_llvm_flow *current_branch = get_current_flow(ctx);
@@ -3149,6 +3165,7 @@ void ac_build_endif(struct ac_llvm_context *ctx, int label_id)
set_basicblock_name(current_branch->next_block, "endif", label_id);
ctx->flow->depth--;
ac_branch_exited(ctx);
}
void ac_build_endloop(struct ac_llvm_context *ctx, int label_id)
@@ -3162,6 +3179,7 @@ void ac_build_endloop(struct ac_llvm_context *ctx, int label_id)
LLVMPositionBuilderAtEnd(ctx->builder, current_loop->next_block);
set_basicblock_name(current_loop->next_block, "endloop", label_id);
ctx->flow->depth--;
ac_branch_exited(ctx);
}
void ac_build_ifcc(struct ac_llvm_context *ctx, LLVMValueRef cond, int label_id)