summaryrefslogtreecommitdiffstats
path: root/src/compiler
diff options
context:
space:
mode:
Diffstat (limited to 'src/compiler')
-rw-r--r--src/compiler/nir/nir_opt_loop_unroll.c31
1 files changed, 17 insertions, 14 deletions
diff --git a/src/compiler/nir/nir_opt_loop_unroll.c b/src/compiler/nir/nir_opt_loop_unroll.c
index 955dfede694..a1ad0e59814 100644
--- a/src/compiler/nir/nir_opt_loop_unroll.c
+++ b/src/compiler/nir/nir_opt_loop_unroll.c
@@ -483,9 +483,10 @@ is_loop_small_enough_to_unroll(nir_shader *shader, nir_loop_info *li)
}
static bool
-process_loops(nir_shader *sh, nir_cf_node *cf_node, bool *innermost_loop)
+process_loops(nir_shader *sh, nir_cf_node *cf_node, bool *has_nested_loop_out)
{
bool progress = false;
+ bool has_nested_loop = false;
nir_loop *loop;
switch (cf_node->type) {
@@ -494,32 +495,32 @@ process_loops(nir_shader *sh, nir_cf_node *cf_node, bool *innermost_loop)
case nir_cf_node_if: {
nir_if *if_stmt = nir_cf_node_as_if(cf_node);
foreach_list_typed_safe(nir_cf_node, nested_node, node, &if_stmt->then_list)
- progress |= process_loops(sh, nested_node, innermost_loop);
+ progress |= process_loops(sh, nested_node, has_nested_loop_out);
foreach_list_typed_safe(nir_cf_node, nested_node, node, &if_stmt->else_list)
- progress |= process_loops(sh, nested_node, innermost_loop);
+ progress |= process_loops(sh, nested_node, has_nested_loop_out);
return progress;
}
case nir_cf_node_loop: {
loop = nir_cf_node_as_loop(cf_node);
foreach_list_typed_safe(nir_cf_node, nested_node, node, &loop->body)
- progress |= process_loops(sh, nested_node, innermost_loop);
+ progress |= process_loops(sh, nested_node, &has_nested_loop);
+
break;
}
default:
unreachable("unknown cf node type");
}
- if (*innermost_loop) {
- /* Don't attempt to unroll outer loops or a second inner loop in
- * this pass wait until the next pass as we have altered the cf.
- */
- *innermost_loop = false;
+ /* Don't attempt to unroll a second inner loop in this pass, wait until the
+ * next pass as we have altered the cf.
+ */
+ if (!progress) {
- if (loop->info->limiting_terminator == NULL)
- return progress;
+ if (has_nested_loop || loop->info->limiting_terminator == NULL)
+ goto exit;
if (!is_loop_small_enough_to_unroll(sh, loop->info))
- return progress;
+ goto exit;
if (loop->info->is_trip_count_known) {
simple_unroll(loop);
@@ -555,6 +556,8 @@ process_loops(nir_shader *sh, nir_cf_node *cf_node, bool *innermost_loop)
}
}
+exit:
+ *has_nested_loop_out = true;
return progress;
}
@@ -567,9 +570,9 @@ nir_opt_loop_unroll_impl(nir_function_impl *impl,
nir_metadata_require(impl, nir_metadata_block_index);
foreach_list_typed_safe(nir_cf_node, node, node, &impl->body) {
- bool innermost_loop = true;
+ bool has_nested_loop = false;
progress |= process_loops(impl->function->shader, node,
- &innermost_loop);
+ &has_nested_loop);
}
if (progress)