nir/dead_cf: Inline cf_node_has_side_effects
We want to handle live SSA values differently and it's going to involve walking the instructions. We can make it a single instruction walk if we combine it with cf_node_has_side_effects. Reviewed-by: Timothy Arceri <tarceri@itsqueeze.com>
This commit is contained in:
parent
367b0ede4d
commit
b50465d197
|
@ -132,45 +132,6 @@ opt_constant_if(nir_if *if_stmt, bool condition)
|
|||
nir_cf_node_remove(&if_stmt->cf_node);
|
||||
}
|
||||
|
||||
static bool
|
||||
cf_node_has_side_effects(nir_cf_node *node)
|
||||
{
|
||||
nir_foreach_block_in_cf_node(block, node) {
|
||||
bool inside_loop = node->type == nir_cf_node_loop;
|
||||
for (nir_cf_node *n = &block->cf_node; !inside_loop && n != node; n = n->parent) {
|
||||
if (n->type == nir_cf_node_loop)
|
||||
inside_loop = true;
|
||||
}
|
||||
|
||||
nir_foreach_instr(instr, block) {
|
||||
if (instr->type == nir_instr_type_call)
|
||||
return true;
|
||||
|
||||
/* Return instructions can cause us to skip over other side-effecting
|
||||
* instructions after the loop, so consider them to have side effects
|
||||
* here.
|
||||
*
|
||||
* When the block is not inside a loop, break and continue might also
|
||||
* cause a skip.
|
||||
*/
|
||||
|
||||
if (instr->type == nir_instr_type_jump &&
|
||||
(!inside_loop || nir_instr_as_jump(instr)->type == nir_jump_return))
|
||||
return true;
|
||||
|
||||
if (instr->type != nir_instr_type_intrinsic)
|
||||
continue;
|
||||
|
||||
nir_intrinsic_instr *intrin = nir_instr_as_intrinsic(instr);
|
||||
if (!(nir_intrinsic_infos[intrin->intrinsic].flags &
|
||||
NIR_INTRINSIC_CAN_ELIMINATE))
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
static bool
|
||||
def_not_live_out(nir_ssa_def *def, void *state)
|
||||
{
|
||||
|
@ -207,8 +168,38 @@ node_is_dead(nir_cf_node *node)
|
|||
nir_block_first_instr(after)->type == nir_instr_type_phi)
|
||||
return false;
|
||||
|
||||
if (cf_node_has_side_effects(node))
|
||||
return false;
|
||||
nir_foreach_block_in_cf_node(block, node) {
|
||||
bool inside_loop = node->type == nir_cf_node_loop;
|
||||
for (nir_cf_node *n = &block->cf_node;
|
||||
!inside_loop && n != node; n = n->parent) {
|
||||
if (n->type == nir_cf_node_loop)
|
||||
inside_loop = true;
|
||||
}
|
||||
|
||||
nir_foreach_instr(instr, block) {
|
||||
if (instr->type == nir_instr_type_call)
|
||||
return true;
|
||||
|
||||
/* Return instructions can cause us to skip over other side-effecting
|
||||
* instructions after the loop, so consider them to have side effects
|
||||
* here.
|
||||
*
|
||||
* When the block is not inside a loop, break and continue might also
|
||||
* cause a skip.
|
||||
*/
|
||||
if (instr->type == nir_instr_type_jump &&
|
||||
(!inside_loop || nir_instr_as_jump(instr)->type == nir_jump_return))
|
||||
return false;
|
||||
|
||||
if (instr->type != nir_instr_type_intrinsic)
|
||||
continue;
|
||||
|
||||
nir_intrinsic_instr *intrin = nir_instr_as_intrinsic(instr);
|
||||
if (!(nir_intrinsic_infos[intrin->intrinsic].flags &
|
||||
NIR_INTRINSIC_CAN_ELIMINATE))
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
nir_function_impl *impl = nir_cf_node_get_function(node);
|
||||
nir_metadata_require(impl, nir_metadata_live_ssa_defs |
|
||||
|
|
Loading…
Reference in New Issue