From 34261b108438a6d9d568f0cf81158fdc84d95fdb Mon Sep 17 00:00:00 2001 From: Lionel Landwerlin Date: Wed, 20 Apr 2022 10:54:36 +0300 Subject: [PATCH] nir/lower_shader_calls: don't insert code after break/continue When moving code from below to the insertion cursor point, if the cursor points to a jump instruction, don't bother inserting the code. It would break the break/continue assumptions of NIR and would not be executed anyway. Signed-off-by: Lionel Landwerlin Fixes: 8dfb240b1f06 ("nir: Add raytracing shader call lowering pass.") Reviewed-by: Jason Ekstrand Part-of: (cherry picked from commit 9cf986dcff3c4364aacea5f36afdae7c3d3957f5) --- .pick_status.json | 2 +- src/compiler/nir/nir_lower_shader_calls.c | 28 ++++++++++++++++++++++- 2 files changed, 28 insertions(+), 2 deletions(-) diff --git a/.pick_status.json b/.pick_status.json index 5b5e9124221..ac0f909a93a 100644 --- a/.pick_status.json +++ b/.pick_status.json @@ -2110,7 +2110,7 @@ "description": "nir/lower_shader_calls: don't insert code after break/continue", "nominated": true, "nomination_type": 1, - "resolution": 0, + "resolution": 1, "main_sha": null, "because_sha": "8dfb240b1f063307aa5e53fb1bd0865105eef986" }, diff --git a/src/compiler/nir/nir_lower_shader_calls.c b/src/compiler/nir/nir_lower_shader_calls.c index 4a2f36b2c89..155ba35e932 100644 --- a/src/compiler/nir/nir_lower_shader_calls.c +++ b/src/compiler/nir/nir_lower_shader_calls.c @@ -729,6 +729,21 @@ rewrite_phis_to_pred(nir_block *block, nir_block *pred) } } +static bool +cursor_is_after_jump(nir_cursor cursor) +{ + switch (cursor.option) { + case nir_cursor_before_instr: + case nir_cursor_before_block: + return false; + case nir_cursor_after_instr: + return cursor.instr->type == nir_instr_type_jump; + case nir_cursor_after_block: + return nir_block_ends_in_jump(cursor.block);; + } + unreachable("Invalid cursor option"); +} + /** Flattens if ladders leading up to a resume * * Given a resume_instr, this function flattens any if ladders leading to the @@ -948,7 +963,18 @@ found_resume: nir_cf_extract(&cf_list, nir_after_instr(resume_instr), nir_after_cf_list(child_list)); } - b->cursor = nir_cf_reinsert(&cf_list, b->cursor); + + if (cursor_is_after_jump(b->cursor)) { + /* If the resume instruction is in a loop, it's possible cf_list ends + * in a break or continue instruction, in which case we don't want to + * insert anything. It's also possible we have an early return if + * someone hasn't lowered those yet. In either case, nothing after that + * point executes in this context so we can delete it. + */ + nir_cf_delete(&cf_list); + } else { + b->cursor = nir_cf_reinsert(&cf_list, b->cursor); + } if (!resume_node) { /* We want the resume to be the first "interesting" instruction */