public inbox for linux-kbuild@vger.kernel.org
 help / color / mirror / Atom feed
From: Petr Pavlu <petr.pavlu@suse.com>
To: Sami Tolvanen <samitolvanen@google.com>
Cc: Masahiro Yamada <masahiroy@kernel.org>,
	Luis Chamberlain <mcgrof@kernel.org>,
	Miguel Ojeda <ojeda@kernel.org>,
	Greg Kroah-Hartman <gregkh@linuxfoundation.org>,
	Matthew Maurer <mmaurer@google.com>,
	Alex Gaynor <alex.gaynor@gmail.com>, Gary Guo <gary@garyguo.net>,
	Petr Pavlu <petr.pavlu@suse.com>,
	Daniel Gomez <da.gomez@samsung.com>, Neal Gompa <neal@gompa.dev>,
	Hector Martin <marcan@marcan.st>, Janne Grunau <j@jannau.net>,
	Miroslav Benes <mbenes@suse.cz>,
	Asahi Linux <asahi@lists.linux.dev>,
	Sedat Dilek <sedat.dilek@gmail.com>,
	linux-kbuild@vger.kernel.org, linux-kernel@vger.kernel.org,
	linux-modules@vger.kernel.org, rust-for-linux@vger.kernel.org
Subject: Re: [PATCH v4 13/19] gendwarfksyms: Add symbol versioning
Date: Tue, 22 Oct 2024 13:48:14 +0200	[thread overview]
Message-ID: <8fa10131-fae2-4052-b541-e4a6ef570d63@suse.com> (raw)
In-Reply-To: <20241008183823.36676-34-samitolvanen@google.com>

On 10/8/24 20:38, Sami Tolvanen wrote:
> Calculate symbol versions from the fully expanded type strings in
> type_map, and output the versions in a genksyms-compatible format.
> 
> Signed-off-by: Sami Tolvanen <samitolvanen@google.com>
> Acked-by: Neal Gompa <neal@gompa.dev>
> ---
>  scripts/gendwarfksyms/dwarf.c         |  25 +++++-
>  scripts/gendwarfksyms/gendwarfksyms.c |  11 ++-
>  scripts/gendwarfksyms/gendwarfksyms.h |  13 ++-
>  scripts/gendwarfksyms/symbols.c       |  59 +++++++++++++
>  scripts/gendwarfksyms/types.c         | 122 +++++++++++++++++++++++++-
>  5 files changed, 222 insertions(+), 8 deletions(-)
> 
> diff --git a/scripts/gendwarfksyms/dwarf.c b/scripts/gendwarfksyms/dwarf.c
> index e1a9e9061b1d..a47a3a0f7a69 100644
> --- a/scripts/gendwarfksyms/dwarf.c
> +++ b/scripts/gendwarfksyms/dwarf.c
> @@ -723,12 +723,33 @@ static int process_type(struct state *state, struct die *parent, Dwarf_Die *die)
>  /*
>   * Exported symbol processing
>   */
> +static struct die *get_symbol_cache(struct state *state, Dwarf_Die *die)
> +{
> +	struct die *cache;
> +
> +	cache = die_map_get(die, DIE_SYMBOL);
> +
> +	if (cache->state != DIE_INCOMPLETE)
> +		return NULL; /* We already processed a symbol for this DIE */
> +
> +	cache->tag = dwarf_tag(die);
> +	return cache;
> +}
> +
>  static void process_symbol(struct state *state, Dwarf_Die *die,
>  			   die_callback_t process_func)
>  {
> +	struct die *cache;
> +
> +	symbol_set_die(state->sym, die);
> +
> +	cache = get_symbol_cache(state, die);
> +	if (!cache)
> +		return;
> +
>  	debug("%s", state->sym->name);
> -	check(process_func(state, NULL, die));
> -	state->sym->state = SYMBOL_MAPPED;
> +	check(process_func(state, cache, die));
> +	cache->state = DIE_SYMBOL;
>  	if (dump_dies)
>  		fputs("\n", stderr);
>  }
> diff --git a/scripts/gendwarfksyms/gendwarfksyms.c b/scripts/gendwarfksyms/gendwarfksyms.c
> index 24c87523fc3a..e90d909d259b 100644
> --- a/scripts/gendwarfksyms/gendwarfksyms.c
> +++ b/scripts/gendwarfksyms/gendwarfksyms.c
> @@ -23,6 +23,8 @@ int dump_dies;
>  int dump_die_map;
>  /* Print out type strings (i.e. type_map) */
>  int dump_types;
> +/* Print out expanded type strings used for symbol versions */
> +int dump_versions;
>  /* Write a symtypes file */
>  int symtypes;
>  static const char *symtypes_file;
> @@ -35,6 +37,7 @@ static void usage(void)
>  	      "      --dump-dies      Dump DWARF DIE contents\n"
>  	      "      --dump-die-map   Print debugging information about die_map changes\n"
>  	      "      --dump-types     Dump type strings\n"
> +	      "      --dump-versions  Dump expanded type strings used for symbol versions\n"
>  	      "  -T, --symtypes file  Write a symtypes file\n"
>  	      "  -h, --help           Print this message\n"
>  	      "\n",
> @@ -69,9 +72,10 @@ static int process_module(Dwfl_Module *mod, void **userdata, const char *name,
>  	} while (cu);
>  
>  	/*
> -	 * Use die_map to expand type strings and write them to `symfile`.
> +	 * Use die_map to expand type strings, write them to `symfile`, and
> +	 * calculate symbol versions.
>  	 */
> -	generate_symtypes(symfile);
> +	generate_symtypes_and_versions(symfile);
>  	die_map_free();
>  
>  	return DWARF_CB_OK;
> @@ -92,6 +96,7 @@ int main(int argc, char **argv)
>  				 { "dump-dies", 0, &dump_dies, 1 },
>  				 { "dump-die-map", 0, &dump_die_map, 1 },
>  				 { "dump-types", 0, &dump_types, 1 },
> +				 { "dump-versions", 0, &dump_versions, 1 },
>  				 { "symtypes", 1, NULL, 'T' },
>  				 { "help", 0, NULL, 'h' },
>  				 { 0, 0, NULL, 0 } };
> @@ -167,5 +172,7 @@ int main(int argc, char **argv)
>  	if (symfile)
>  		check(fclose(symfile));
>  
> +	symbol_print_versions();
> +
>  	return 0;
>  }
> diff --git a/scripts/gendwarfksyms/gendwarfksyms.h b/scripts/gendwarfksyms/gendwarfksyms.h
> index e47b5e967520..814f53ef799e 100644
> --- a/scripts/gendwarfksyms/gendwarfksyms.h
> +++ b/scripts/gendwarfksyms/gendwarfksyms.h
> @@ -26,6 +26,7 @@ extern int debug;
>  extern int dump_dies;
>  extern int dump_die_map;
>  extern int dump_types;
> +extern int dump_versions;
>  extern int symtypes;
>  
>  /*
> @@ -98,6 +99,7 @@ static inline unsigned int addr_hash(uintptr_t addr)
>  enum symbol_state {
>  	SYMBOL_UNPROCESSED,
>  	SYMBOL_MAPPED,
> +	SYMBOL_PROCESSED
>  };
>  
>  struct symbol_addr {
> @@ -112,6 +114,7 @@ struct symbol {
>  	struct hlist_node name_hash;
>  	enum symbol_state state;
>  	uintptr_t die_addr;
> +	unsigned long crc;
>  };
>  
>  typedef void (*symbol_callback_t)(struct symbol *, void *arg);
> @@ -119,6 +122,10 @@ typedef void (*symbol_callback_t)(struct symbol *, void *arg);
>  void symbol_read_exports(FILE *file);
>  void symbol_read_symtab(int fd);
>  struct symbol *symbol_get(const char *name);
> +void symbol_set_die(struct symbol *sym, Dwarf_Die *die);
> +void symbol_set_crc(struct symbol *sym, unsigned long crc);
> +void symbol_for_each(symbol_callback_t func, void *arg);
> +void symbol_print_versions(void);
>  
>  /*
>   * die.c
> @@ -128,7 +135,8 @@ enum die_state {
>  	DIE_INCOMPLETE,
>  	DIE_UNEXPANDED,
>  	DIE_COMPLETE,
> -	DIE_LAST = DIE_COMPLETE
> +	DIE_SYMBOL,
> +	DIE_LAST = DIE_SYMBOL
>  };
>  
>  enum die_fragment_type {
> @@ -158,6 +166,7 @@ static inline const char *die_state_name(enum die_state state)
>  	CASE_CONST_TO_STR(DIE_INCOMPLETE)
>  	CASE_CONST_TO_STR(DIE_UNEXPANDED)
>  	CASE_CONST_TO_STR(DIE_COMPLETE)
> +	CASE_CONST_TO_STR(DIE_SYMBOL)
>  	}
>  
>  	error("unexpected die_state: %d", state);
> @@ -245,6 +254,6 @@ void process_cu(Dwarf_Die *cudie);
>   * types.c
>   */
>  
> -void generate_symtypes(FILE *file);
> +void generate_symtypes_and_versions(FILE *file);
>  
>  #endif /* __GENDWARFKSYMS_H */
> diff --git a/scripts/gendwarfksyms/symbols.c b/scripts/gendwarfksyms/symbols.c
> index e414257333e5..e17f11a02f6e 100644
> --- a/scripts/gendwarfksyms/symbols.c
> +++ b/scripts/gendwarfksyms/symbols.c
> @@ -66,6 +66,36 @@ static unsigned int for_each(const char *name, symbol_callback_t func,
>  	return 0;
>  }
>  
> +static void set_crc(struct symbol *sym, void *data)
> +{
> +	unsigned long *crc = data;
> +
> +	if (sym->state == SYMBOL_PROCESSED && sym->crc != *crc)
> +		warn("overriding version for symbol %s (crc %lx vs. %lx)",
> +		     sym->name, sym->crc, *crc);
> +
> +	sym->state = SYMBOL_PROCESSED;
> +	sym->crc = *crc;
> +}
> +
> +void symbol_set_crc(struct symbol *sym, unsigned long crc)
> +{
> +	if (for_each(sym->name, set_crc, &crc) == 0)
> +		error("no matching symbols: '%s'", sym->name);
> +}
> +
> +static void set_die(struct symbol *sym, void *data)
> +{
> +	sym->die_addr = (uintptr_t)((Dwarf_Die *)data)->addr;
> +	sym->state = SYMBOL_MAPPED;
> +}
> +
> +void symbol_set_die(struct symbol *sym, Dwarf_Die *die)
> +{
> +	if (for_each(sym->name, set_die, die) == 0)
> +		error("no matching symbols: '%s'", sym->name);
> +}
> +
>  static bool is_exported(const char *name)
>  {
>  	return for_each(name, NULL, NULL) > 0;
> @@ -120,6 +150,16 @@ struct symbol *symbol_get(const char *name)
>  	return sym;
>  }
>  
> +void symbol_for_each(symbol_callback_t func, void *arg)
> +{
> +	struct hlist_node *tmp;
> +	struct symbol *sym;
> +
> +	hash_for_each_safe(symbol_names, sym, tmp, name_hash) {
> +		func(sym, arg);
> +	}
> +}
> +
>  typedef void (*elf_symbol_callback_t)(const char *name, GElf_Sym *sym,
>  				      Elf32_Word xndx, void *arg);
>  
> @@ -231,3 +271,22 @@ void symbol_read_symtab(int fd)
>  {
>  	elf_for_each_global(fd, elf_set_symbol_addr, NULL);
>  }
> +
> +void symbol_print_versions(void)
> +{
> +	struct hlist_node *tmp;
> +	struct symbol *sym;
> +
> +	hash_for_each_safe(symbol_names, sym, tmp, name_hash) {
> +		if (sym->state != SYMBOL_PROCESSED)
> +			warn("no information for symbol %s", sym->name);
> +
> +		printf("#SYMVER %s 0x%08lx\n", sym->name, sym->crc);
> +
> +		free((void *)sym->name);
> +		free(sym);
> +	}
> +
> +	hash_init(symbol_addrs);
> +	hash_init(symbol_names);
> +}

I had some minor comment about adjusting the name of function
symbol_print_versions() and possibly changing sym->name to 'char *' on
the v2 of the patch:
https://lore.kernel.org/all/286b1cc5-1757-4f0a-bb66-0875f4608c7e@suse.com/
Please have a look, it seems it felt through the cracks.

In any case, the patch looks ok to me, feel free to add:
Reviewed-by: Petr Pavlu <petr.pavlu@suse.com>

-- 
Thanks,
Petr

  reply	other threads:[~2024-10-22 11:48 UTC|newest]

Thread overview: 40+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2024-10-08 18:38 [PATCH v4 00/19] Implement DWARF modversions Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 01/19] scripts: move genksyms crc32 implementation to a common include Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 02/19] tools: Add gendwarfksyms Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 03/19] gendwarfksyms: Add address matching Sami Tolvanen
2024-10-17 14:08   ` Petr Pavlu
2024-10-17 17:16     ` Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 04/19] gendwarfksyms: Expand base_type Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 05/19] gendwarfksyms: Add a cache for processed DIEs Sami Tolvanen
2024-10-22 11:39   ` Petr Pavlu
2024-10-08 18:38 ` [PATCH v4 06/19] gendwarfksyms: Expand type modifiers and typedefs Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 07/19] gendwarfksyms: Expand subroutine_type Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 08/19] gendwarfksyms: Expand array_type Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 09/19] gendwarfksyms: Expand structure types Sami Tolvanen
2024-10-22 11:42   ` Petr Pavlu
2024-10-08 18:38 ` [PATCH v4 10/19] gendwarfksyms: Limit structure expansion Sami Tolvanen
2024-10-16 14:16   ` Petr Pavlu
2024-10-16 21:21     ` Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 11/19] gendwarfksyms: Add die_map debugging Sami Tolvanen
2024-10-17 14:09   ` Petr Pavlu
2024-10-08 18:38 ` [PATCH v4 12/19] gendwarfksyms: Add symtypes output Sami Tolvanen
2024-10-17 14:13   ` Petr Pavlu
2024-10-17 17:35     ` Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 13/19] gendwarfksyms: Add symbol versioning Sami Tolvanen
2024-10-22 11:48   ` Petr Pavlu [this message]
2024-10-23 17:46     ` Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 14/19] gendwarfksyms: Add support for kABI rules Sami Tolvanen
2024-10-22 14:38   ` Petr Pavlu
2024-10-23 17:47     ` Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 15/19] gendwarfksyms: Add support for reserved and ignored fields Sami Tolvanen
2024-10-23 14:53   ` Petr Pavlu
2024-10-23 21:05     ` Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 16/19] gendwarfksyms: Add support for symbol type pointers Sami Tolvanen
2024-10-23 14:55   ` Petr Pavlu
2024-10-08 18:38 ` [PATCH v4 17/19] export: Add __gendwarfksyms_ptr_ references to exported symbols Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 18/19] kbuild: Add gendwarfksyms as an alternative to genksyms Sami Tolvanen
2024-10-23 14:59   ` Petr Pavlu
2024-10-23 21:14     ` Sami Tolvanen
2024-10-08 18:38 ` [PATCH v4 19/19] Documentation/kbuild: Add DWARF module versioning Sami Tolvanen
2024-10-11 23:42 ` [PATCH v4 00/19] Implement DWARF modversions Luis Chamberlain
2024-10-12  0:30   ` Sami Tolvanen

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=8fa10131-fae2-4052-b541-e4a6ef570d63@suse.com \
    --to=petr.pavlu@suse.com \
    --cc=alex.gaynor@gmail.com \
    --cc=asahi@lists.linux.dev \
    --cc=da.gomez@samsung.com \
    --cc=gary@garyguo.net \
    --cc=gregkh@linuxfoundation.org \
    --cc=j@jannau.net \
    --cc=linux-kbuild@vger.kernel.org \
    --cc=linux-kernel@vger.kernel.org \
    --cc=linux-modules@vger.kernel.org \
    --cc=marcan@marcan.st \
    --cc=masahiroy@kernel.org \
    --cc=mbenes@suse.cz \
    --cc=mcgrof@kernel.org \
    --cc=mmaurer@google.com \
    --cc=neal@gompa.dev \
    --cc=ojeda@kernel.org \
    --cc=rust-for-linux@vger.kernel.org \
    --cc=samitolvanen@google.com \
    --cc=sedat.dilek@gmail.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox