[PATCH 08/15] gendwarfksyms: Expand subroutine_type
From: Sami Tolvanen <samitolvanen@google.com>
Date: 2024-06-17 17:58:40
Also in:
linux-kbuild, lkml, rust-for-linux
Subsystem:
the rest · Maintainer:
Linus Torvalds
Add support for expanding DW_TAG_subroutine_type and the parameters
in DW_TAG_formal_parameter. Use also to expand subprograms.
Example output with --debug:
subprogram(
formal_parameter base_type usize byte_size(8),
formal_parameter base_type usize byte_size(8),
)
-> base_type void;
Signed-off-by: Sami Tolvanen <samitolvanen@google.com>
---
tools/gendwarfksyms/gendwarfksyms.h | 1 +
tools/gendwarfksyms/types.c | 58 ++++++++++++++++++++++++++++-
2 files changed, 58 insertions(+), 1 deletion(-)
diff --git a/tools/gendwarfksyms/gendwarfksyms.h b/tools/gendwarfksyms/gendwarfksyms.h
index 43eff91e2f2f..03d8a4a039c3 100644
--- a/tools/gendwarfksyms/gendwarfksyms.h
+++ b/tools/gendwarfksyms/gendwarfksyms.h@@ -52,6 +52,7 @@ extern bool no_pretty_print; }) /* Consistent aliases (DW_TAG_<type>_type) for DWARF tags */ +#define DW_TAG_formal_parameter_type DW_TAG_formal_parameter #define DW_TAG_typedef_type DW_TAG_typedef /*
diff --git a/tools/gendwarfksyms/types.c b/tools/gendwarfksyms/types.c
index 74b3755c3e16..a56aeaa4f3a1 100644
--- a/tools/gendwarfksyms/types.c
+++ b/tools/gendwarfksyms/types.c@@ -169,6 +169,15 @@ static int process_fqn(struct state *state, struct cached_die *cache, DEFINE_PROCESS_UDATA_ATTRIBUTE(alignment) DEFINE_PROCESS_UDATA_ATTRIBUTE(byte_size) +/* Match functions -- die_match_callback_t */ +#define DEFINE_MATCH(type) \ + static bool match_##type##_type(Dwarf_Die *die) \ + { \ + return dwarf_tag(die) == DW_TAG_##type##_type; \ + } + +DEFINE_MATCH(formal_parameter) + bool match_all(Dwarf_Die *die) { return true;
@@ -206,6 +215,25 @@ static int process_type_attr(struct state *state, struct cached_die *cache, return check(process(state, cache, "base_type void")); } +/* Comma-separated with DW_AT_type */ +static int __process_list_type(struct state *state, struct cached_die *cache, + Dwarf_Die *die, const char *type) +{ + check(process(state, cache, type)); + check(process_type_attr(state, cache, die)); + check(process(state, cache, ",")); + return check(process_linebreak(cache, 0)); +} + +#define DEFINE_PROCESS_LIST_TYPE(type) \ + static int process_##type##_type( \ + struct state *state, struct cached_die *cache, Dwarf_Die *die) \ + { \ + return __process_list_type(state, cache, die, #type " "); \ + } + +DEFINE_PROCESS_LIST_TYPE(formal_parameter) + /* Container types with DW_AT_type */ static int __process_type(struct state *state, struct cached_die *cache, Dwarf_Die *die, const char *type)
@@ -240,6 +268,30 @@ DEFINE_PROCESS_TYPE(shared) DEFINE_PROCESS_TYPE(volatile) DEFINE_PROCESS_TYPE(typedef) +static int __process_subroutine_type(struct state *state, + struct cached_die *cache, Dwarf_Die *die, + const char *type) +{ + check(process(state, cache, type)); + check(process(state, cache, "(")); + check(process_linebreak(cache, 1)); + /* Parameters */ + check(process_die_container(state, cache, die, process_type, + match_formal_parameter_type)); + check(process_linebreak(cache, -1)); + check(process(state, cache, ")")); + process_linebreak(cache, 0); + /* Return type */ + check(process(state, cache, "-> ")); + return check(process_type_attr(state, cache, die)); +} + +static int process_subroutine_type(struct state *state, + struct cached_die *cache, Dwarf_Die *die) +{ + return check(__process_subroutine_type(state, cache, die, + "subroutine_type")); +} static int process_base_type(struct state *state, struct cached_die *cache, Dwarf_Die *die) {
@@ -324,8 +376,11 @@ static int process_type(struct state *state, struct cached_die *parent, PROCESS_TYPE(rvalue_reference) PROCESS_TYPE(shared) PROCESS_TYPE(volatile) + /* Subtypes */ + PROCESS_TYPE(formal_parameter) /* Other types */ PROCESS_TYPE(base) + PROCESS_TYPE(subroutine) PROCESS_TYPE(typedef) default: debug("unimplemented type: %x", tag);
@@ -346,7 +401,8 @@ static int process_type(struct state *state, struct cached_die *parent, */ static int process_subprogram(struct state *state, Dwarf_Die *die) { - return check(process(state, NULL, "subprogram;\n")); + check(__process_subroutine_type(state, NULL, die, "subprogram")); + return check(process(state, NULL, ";\n")); } static int process_variable(struct state *state, Dwarf_Die *die)
--
2.45.2.627.g7a2c4fd464-goog