From 18ca6c37f0f8eb117013f0c845735b803ac27a4d Mon Sep 17 00:00:00 2001 From: Dave Airlie Date: Tue, 27 Oct 2020 07:28:04 +1000 Subject: [PATCH] nir: add a function usage tracker allows dropping old fns Reviewed-by: Alyssa Rosenzweig Part-of: --- src/compiler/nir/nir.h | 1 + src/compiler/nir/nir_functions.c | 51 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 52 insertions(+) diff --git a/src/compiler/nir/nir.h b/src/compiler/nir/nir.h index 5dfa71c..9850d33 100644 --- a/src/compiler/nir/nir.h +++ b/src/compiler/nir/nir.h @@ -4835,6 +4835,7 @@ void nir_inline_function_impl(struct nir_builder *b, nir_def **params, struct hash_table *shader_var_remap); bool nir_inline_functions(nir_shader *shader); +void nir_cleanup_functions(nir_shader *shader); bool nir_link_shader_functions(nir_shader *shader, const nir_shader *link_shader); diff --git a/src/compiler/nir/nir_functions.c b/src/compiler/nir/nir_functions.c index a70b5f9..6d39ac0 100644 --- a/src/compiler/nir/nir_functions.c +++ b/src/compiler/nir/nir_functions.c @@ -417,3 +417,54 @@ nir_link_shader_functions(nir_shader *shader, return overall_progress; } + +static void +nir_mark_used_functions(struct nir_function *func, struct set *used_funcs); + +static bool mark_used_pass_cb(struct nir_builder *b, + nir_instr *instr, void *data) +{ + struct set *used_funcs = data; + if (instr->type != nir_instr_type_call) + return false; + nir_call_instr *call = nir_instr_as_call(instr); + + _mesa_set_add(used_funcs, call->callee); + + nir_mark_used_functions(call->callee, used_funcs); + return true; +} + +static void +nir_mark_used_functions(struct nir_function *func, struct set *used_funcs) +{ + if (func->impl) { + nir_function_instructions_pass(func->impl, + mark_used_pass_cb, + nir_metadata_none, + used_funcs); + } +} + +void +nir_cleanup_functions(nir_shader *nir) +{ + if (!nir->options->driver_functions) { + nir_remove_non_entrypoints(nir); + return; + } + + struct set *used_funcs = _mesa_set_create(NULL, _mesa_hash_pointer, + _mesa_key_pointer_equal); + foreach_list_typed_safe(nir_function, func, node, &nir->functions) { + if (func->is_entrypoint) { + _mesa_set_add(used_funcs, func); + nir_mark_used_functions(func, used_funcs); + } + } + foreach_list_typed_safe(nir_function, func, node, &nir->functions) { + if (!_mesa_set_search(used_funcs, func)) + exec_node_remove(&func->node); + } + _mesa_set_destroy(used_funcs, NULL); +} -- 2.7.4