diff options
author | H.J. Lu <hjl.tools@gmail.com> | 2020-03-19 21:00:19 -0700 |
---|---|---|
committer | H.J. Lu <hjl.tools@gmail.com> | 2020-03-19 21:00:58 -0700 |
commit | c3a1714ce7806002726a60c0db09371425fe3097 (patch) | |
tree | 99377ebd529a95e5f653d10d02e48af905d1e3ea /bfd/plugin.c | |
parent | Silence warnings due to plugin API change (diff) | |
download | binutils-gdb-c3a1714ce7806002726a60c0db09371425fe3097.tar.gz binutils-gdb-c3a1714ce7806002726a60c0db09371425fe3097.tar.bz2 binutils-gdb-c3a1714ce7806002726a60c0db09371425fe3097.zip |
plugin: Use LDPT_ADD_SYMBOLS_V2 to get symbol type
Since LTO plugin may generate more than one ltrans.o file from one input
IR object as LTO wrapper ignores -flto-partition=none:
lto-wrapper.c:608:
604 /* Drop arguments that we want to take from the link line. */
605 case OPT_flto_:
606 case OPT_flto:
607 case OPT_flto_partition_:
608 continue;
the LTO wrapper approach is not only slow but also unreliable. Since
the LTO plugin API has been extended to add LDPT_ADD_SYMBOLS_V2 with
symbol type and section kind, we can use LDPT_ADD_SYMBOLS_V2 to get
symbol type, instead of invoking the LTO wrapper.
PR binutils/25640
* plugin.c (plugin_list_entry): Add has_symbol_type.
(add_symbols_v2): New function.
(bfd_plugin_open_input): Don't invoke LTO wrapper if LTO plugin
provides symbol type.
(try_load_plugin): Add LDPT_ADD_SYMBOLS_V2.
(bfd_plugin_canonicalize_symtab): Use LTO plugin symbol type if
available.
Diffstat (limited to 'bfd/plugin.c')
-rw-r--r-- | bfd/plugin.c | 66 |
1 files changed, 52 insertions, 14 deletions
diff --git a/bfd/plugin.c b/bfd/plugin.c index a0f172d3637..13549d24e7e 100644 --- a/bfd/plugin.c +++ b/bfd/plugin.c @@ -136,6 +136,7 @@ struct plugin_list_entry asymbol **real_syms; int lto_nsyms; const struct ld_plugin_symbol *lto_syms; + bfd_boolean has_symbol_type; struct plugin_list_entry *next; @@ -503,6 +504,14 @@ add_symbols (void * handle, return LDPS_OK; } +static enum ld_plugin_status +add_symbols_v2 (void *handle, int nsyms, + const struct ld_plugin_symbol *syms) +{ + current_plugin->has_symbol_type = TRUE; + return add_symbols (handle, nsyms, syms); +} + int bfd_plugin_open_input (bfd *ibfd, struct ld_plugin_input_file *file) { @@ -560,7 +569,8 @@ try_claim (bfd *abfd) current_plugin->claim_file (&file, &claimed); if (claimed) { - if (current_plugin->all_symbols_read) + if (current_plugin->all_symbols_read + && !current_plugin->has_symbol_type) { struct plugin_data_struct *plugin_data = abfd->tdata.plugin_data; @@ -602,7 +612,7 @@ try_load_plugin (const char *pname, bfd *abfd, bfd_boolean build_list_p) { void *plugin_handle; - struct ld_plugin_tv tv[12]; + struct ld_plugin_tv tv[13]; int i; ld_plugin_onload onload; enum ld_plugin_status status; @@ -665,6 +675,10 @@ try_load_plugin (const char *pname, tv[i].tv_tag = LDPT_ADD_SYMBOLS; tv[i].tv_u.tv_add_symbols = add_symbols; + ++i; + tv[i].tv_tag = LDPT_ADD_SYMBOLS_V2; + tv[i].tv_u.tv_add_symbols = add_symbols_v2; + if (get_lto_wrapper (plugin_list_iter)) { ++i; @@ -977,9 +991,15 @@ bfd_plugin_canonicalize_symtab (bfd *abfd, struct plugin_data_struct *plugin_data = abfd->tdata.plugin_data; long nsyms = plugin_data->nsyms; const struct ld_plugin_symbol *syms = plugin_data->syms; - static asection fake_section - = BFD_FAKE_SECTION (fake_section, NULL, "plug", 0, + static asection fake_text_section + = BFD_FAKE_SECTION (fake_text_section, NULL, "plug", 0, SEC_ALLOC | SEC_LOAD | SEC_CODE | SEC_HAS_CONTENTS); + static asection fake_data_section + = BFD_FAKE_SECTION (fake_data_section, NULL, "plug", 0, + SEC_ALLOC | SEC_LOAD | SEC_DATA | SEC_HAS_CONTENTS); + static asection fake_bss_section + = BFD_FAKE_SECTION (fake_bss_section, NULL, "plug", 0, + SEC_ALLOC); static asection fake_common_section = BFD_FAKE_SECTION (fake_common_section, NULL, "plug", 0, SEC_IS_COMMON); int i, j; @@ -1014,16 +1034,34 @@ bfd_plugin_canonicalize_symtab (bfd *abfd, break; case LDPK_DEF: case LDPK_WEAKDEF: - s->section = &fake_section; - if (real_nsyms) - /* Use real LTO symbols if possible. */ - for (j = 0; j < real_nsyms; j++) - if (real_syms[j]->name - && strcmp (syms[i].name, real_syms[j]->name) == 0) - { - s->section = real_syms[j]->section; - break; - } + if (current_plugin->has_symbol_type) + switch (syms[i].symbol_type) + { + case LDST_UNKNOWN: + /* What is the best fake section for LDST_UNKNOWN? */ + case LDST_FUNCTION: + s->section = &fake_text_section; + break; + case LDST_VARIABLE: + if (syms[i].section_kind == LDSSK_BSS) + s->section = &fake_bss_section; + else + s->section = &fake_data_section; + break; + } + else + { + s->section = &fake_text_section; + if (real_nsyms) + /* Use real LTO symbols if possible. */ + for (j = 0; j < real_nsyms; j++) + if (real_syms[j]->name + && strcmp (syms[i].name, real_syms[j]->name) == 0) + { + s->section = real_syms[j]->section; + break; + } + } break; default: BFD_ASSERT (0); |