[binutils-gdb] ELF OSABI matching
Alan Modra
amodra@sourceware.org
Sun Jan 4 07:31:32 GMT 2026
https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;h=ef6aff2be44b172a874df036c7d270301b47005a
commit ef6aff2be44b172a874df036c7d270301b47005a
Author: Alan Modra <amodra@gmail.com>
Date: Sat Jan 3 13:51:21 2026 +1030
ELF OSABI matching
Currently a binutils ELF target with ELF_OSABI defined to something
other than the default ELFOSABI_NONE will only accept object files
with e_ident[EI_OSABI] having the value ELF_OSABI. An ELF target with
ELF_OSABI as ELFOSABI_NONE will match any e_ident[EI_OSABI] value, and
typically that target's object files will have ELFOSABI_NONE or one
other value in e_ident[EI_OSABI]. Given an object file with that
"other value" we'd like to be able to choose the correct target but
currently have no way to do so. This patch is a step towards
implementing better target matching.
It does so by adding an ELF_OSABI_EXACT to the target description,
setting that true for all targets that currently define ELF_OSABI, and
testing the new flag for exact matching. This will allow a future
patch to define ELF_OSABI without forcing exact matching but giving a
hint as to the best target match.
Some other tweaks are done as shown by the changelog below but no
user functional changes should be seen with this patch.
* elf-bfd.h (struct elf_backend_data): Add osabi_exact.
* elf.c (_bfd_elf_final_write_processing): Only set e_ident
from elf_osabi when osabi_exact.
* elfcode.h (elf_object_p): Test osabi_exact to reject
mismatching e_ident. Remove unnecessary EM_NONE test.
* elfcore.h (elf_core_file_p): Likewise.
* elfxx-target.h (ELF_OSABI_EXACT): Provide default of 0,
and init elfNN_bed.
(elf_match_priority): Handle ELF_OSABI_EXACT.
* elf32-arm.c (ELF_OSABI_EXACT): Define and undef along with
ELF_OSABI.
* elf32-hppa.c: Likewise.
* elf32-i386.c: Likewise.
* elf32-mips.c: Likewise.
* elf32-ppc.c: Likewise.
* elf32-tic6x.c: Likewise.
* elf32-visium.c: Likewise.
* elf64-alpha.c: Likewise.
* elf64-hppa.c: Likewise.
* elf64-ia64-vms.c: Likewise.
* elf64-mips.c: Likewise.
* elf64-ppc.c: Likewise.
* elf64-sparc.c: Likewise.
* elf64-x86-64.c: Likewise.
* elfn32-mips.c: Likewise.
* elfnn-ia64.c: Likewise.
* elf32-msp430.c: Likewise. Don't define ELF_OSABI to
ELFOSABI_NONE.
Diff:
---
bfd/elf-bfd.h | 4 ++++
bfd/elf.c | 2 +-
bfd/elf32-arm.c | 3 +++
bfd/elf32-hppa.c | 1 +
bfd/elf32-i386.c | 7 ++++++-
bfd/elf32-mips.c | 3 +++
bfd/elf32-msp430.c | 3 ++-
bfd/elf32-ppc.c | 3 +++
bfd/elf32-tic6x.c | 4 ++++
bfd/elf32-visium.c | 1 +
bfd/elf64-alpha.c | 2 ++
bfd/elf64-hppa.c | 1 +
bfd/elf64-ia64-vms.c | 2 ++
bfd/elf64-mips.c | 2 ++
bfd/elf64-ppc.c | 2 ++
bfd/elf64-sparc.c | 3 +++
bfd/elf64-x86-64.c | 5 +++++
bfd/elfcode.h | 4 +---
bfd/elfcore.h | 4 +---
bfd/elfn32-mips.c | 2 ++
bfd/elfnn-ia64.c | 2 ++
bfd/elfxx-target.h | 9 ++++++++-
22 files changed, 59 insertions(+), 10 deletions(-)
diff --git a/bfd/elf-bfd.h b/bfd/elf-bfd.h
index efe40e10605..b2aeb2ba0ca 100644
--- a/bfd/elf-bfd.h
+++ b/bfd/elf-bfd.h
@@ -1023,6 +1023,10 @@ struct elf_backend_data
/* Target OS. */
ENUM_BITFIELD (elf_target_os) target_os : 2;
+ /* True if object files must have exactly matching osabi. False if
+ other osabi values are allowed. */
+ unsigned osabi_exact : 1;
+
/* The maximum page size for this backend. */
unsigned maxpagesize;
diff --git a/bfd/elf.c b/bfd/elf.c
index d2cf2bb4b9c..8b6dd3ce370 100644
--- a/bfd/elf.c
+++ b/bfd/elf.c
@@ -13486,7 +13486,7 @@ _bfd_elf_final_write_processing (bfd *abfd)
Elf_Internal_Ehdr *i_ehdrp = elf_elfheader (abfd);
elf_backend_data *bed = get_elf_backend_data (abfd);
- if (i_ehdrp->e_ident[EI_OSABI] == ELFOSABI_NONE)
+ if (bed->osabi_exact && i_ehdrp->e_ident[EI_OSABI] == ELFOSABI_NONE)
i_ehdrp->e_ident[EI_OSABI] = bed->elf_osabi;
if (i_ehdrp->e_ident[EI_OSABI] == ELFOSABI_SOLARIS
diff --git a/bfd/elf32-arm.c b/bfd/elf32-arm.c
index 9465efc5953..e0573d53ef0 100644
--- a/bfd/elf32-arm.c
+++ b/bfd/elf32-arm.c
@@ -20277,6 +20277,8 @@ elf32_arm_backend_symbol_processing (bfd *abfd, asymbol *sym)
#define elf_match_priority 128
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_ARM_FDPIC
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
/* Like elf32_arm_link_hash_table_create -- but overrides
appropriately for FDPIC. */
@@ -20335,6 +20337,7 @@ elf32_arm_fdpic_omit_section_dynsym (bfd *output_bfd ATTRIBUTE_UNUSED,
#undef elf_match_priority
#undef ELF_OSABI
+#undef ELF_OSABI_EXACT
#undef elf_backend_omit_section_dynsym
/* VxWorks Targets. */
diff --git a/bfd/elf32-hppa.c b/bfd/elf32-hppa.c
index 260844985d3..e3aa67c3fc6 100644
--- a/bfd/elf32-hppa.c
+++ b/bfd/elf32-hppa.c
@@ -4539,6 +4539,7 @@ elf32_hppa_elf_get_symbol_type (Elf_Internal_Sym *elf_sym, int type)
#define ELF_MACHINE_CODE EM_PARISC
#define ELF_MAXPAGESIZE 0x1000
#define ELF_OSABI ELFOSABI_HPUX
+#define ELF_OSABI_EXACT 1
#define elf32_bed elf32_hppa_hpux_bed
#include "elf32-target.h"
diff --git a/bfd/elf32-i386.c b/bfd/elf32-i386.c
index a367fd9f6f0..be8c676c833 100644
--- a/bfd/elf32-i386.c
+++ b/bfd/elf32-i386.c
@@ -4617,6 +4617,8 @@ elf_i386_add_glibc_version_dependency
#define TARGET_LITTLE_NAME "elf32-i386-freebsd"
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_FREEBSD
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
/* The kernel recognizes executables as valid only if they carry a
"FreeBSD" label in the ELF header. So we put this label on all
@@ -4665,6 +4667,7 @@ elf_i386_fbsd_init_file_header (bfd *abfd, struct bfd_link_info *info)
/* Restore default: we cannot use ELFOSABI_SOLARIS, otherwise ELFOSABI_NONE
objects won't be recognized. */
#undef ELF_OSABI
+#undef ELF_OSABI_EXACT
#undef elf32_bed
#define elf32_bed elf32_i386_sol2_bed
@@ -4708,6 +4711,7 @@ elf32_iamcu_elf_object_p (bfd *abfd)
#undef ELF_TARGET_OS
#undef ELF_OSABI
+#undef ELF_OSABI_EXACT
#undef elf32_bed
#define elf32_bed elf32_iamcu_bed
@@ -4735,7 +4739,6 @@ elf32_iamcu_elf_object_p (bfd *abfd)
#define TARGET_LITTLE_SYM i386_elf32_vxworks_vec
#undef TARGET_LITTLE_NAME
#define TARGET_LITTLE_NAME "elf32-i386-vxworks"
-#undef ELF_OSABI
#undef ELF_MAXPAGESIZE
#define ELF_MAXPAGESIZE 0x1000
#undef elf_backend_plt_alignment
@@ -4743,6 +4746,8 @@ elf32_iamcu_elf_object_p (bfd *abfd)
#undef ELF_TARGET_OS
#define ELF_TARGET_OS is_vxworks
+#undef ELF_OSABI
+#undef ELF_OSABI_EXACT
#undef elf_backend_relocs_compatible
#undef elf_backend_add_symbol_hook
diff --git a/bfd/elf32-mips.c b/bfd/elf32-mips.c
index 1df60bda04b..12a95b08ff8 100644
--- a/bfd/elf32-mips.c
+++ b/bfd/elf32-mips.c
@@ -4165,6 +4165,8 @@ static const struct ecoff_debug_swap mips_elf32_ecoff_debug_swap = {
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_FREEBSD
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
#undef elf32_bed
#define elf32_bed elf32_fbsd_tradbed
@@ -4194,6 +4196,7 @@ mips_vxworks_final_write_processing (bfd *abfd)
#define TARGET_BIG_SYM mips_elf32_vxworks_be_vec
#define TARGET_BIG_NAME "elf32-bigmips-vxworks"
#undef ELF_OSABI
+#undef ELF_OSABI_EXACT
#undef elf32_bed
#define elf32_bed elf32_mips_vxworks_bed
diff --git a/bfd/elf32-msp430.c b/bfd/elf32-msp430.c
index cb83f5692be..d7d7730063f 100644
--- a/bfd/elf32-msp430.c
+++ b/bfd/elf32-msp430.c
@@ -2953,6 +2953,7 @@ elf32_msp430_eh_frame_address_size (bfd *abfd,
#define ELF_MACHINE_ALT1 EM_MSP430_OLD
#define ELF_MAXPAGESIZE 4
#define ELF_OSABI ELFOSABI_STANDALONE
+#define ELF_OSABI_EXACT 1
#define TARGET_LITTLE_SYM msp430_elf32_vec
#define TARGET_LITTLE_NAME "elf32-msp430"
@@ -2980,7 +2981,7 @@ elf32_msp430_eh_frame_address_size (bfd *abfd,
#define elf32_bed elf32_msp430_ti_bed
#undef ELF_OSABI
-#define ELF_OSABI ELFOSABI_NONE
+#undef ELF_OSABI_EXACT
static const struct bfd_elf_special_section msp430_ti_elf_special_sections[] =
{
diff --git a/bfd/elf32-ppc.c b/bfd/elf32-ppc.c
index ecbdb91c667..ba9e59ab3b9 100644
--- a/bfd/elf32-ppc.c
+++ b/bfd/elf32-ppc.c
@@ -10433,6 +10433,8 @@ ppc_elf_finish_dynamic_sections (bfd *output_bfd,
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_FREEBSD
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
#undef elf32_bed
#define elf32_bed elf32_powerpc_fbsd_bed
@@ -10450,6 +10452,7 @@ ppc_elf_finish_dynamic_sections (bfd *output_bfd,
#define TARGET_BIG_NAME "elf32-powerpc-vxworks"
#undef ELF_OSABI
+#undef ELF_OSABI_EXACT
#undef ELF_TARGET_OS
#define ELF_TARGET_OS is_vxworks
diff --git a/bfd/elf32-tic6x.c b/bfd/elf32-tic6x.c
index c776f31092e..d5f1259d1f4 100644
--- a/bfd/elf32-tic6x.c
+++ b/bfd/elf32-tic6x.c
@@ -4285,6 +4285,8 @@ elf32_tic6x_write_section (bfd *output_bfd,
#define TARGET_BIG_NAME "elf32-tic6x-linux-be"
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_C6000_LINUX
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
#include "elf32-target.h"
@@ -4301,5 +4303,7 @@ elf32_tic6x_write_section (bfd *output_bfd,
#define TARGET_BIG_NAME "elf32-tic6x-elf-be"
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_C6000_ELFABI
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
#include "elf32-target.h"
diff --git a/bfd/elf32-visium.c b/bfd/elf32-visium.c
index 1771c444c22..7f28c81fda3 100644
--- a/bfd/elf32-visium.c
+++ b/bfd/elf32-visium.c
@@ -852,6 +852,7 @@ visium_elf_print_private_bfd_data (bfd *abfd, void *ptr)
#define ELF_ARCH bfd_arch_visium
#define ELF_MACHINE_CODE EM_VISIUM
#define ELF_OSABI ELFOSABI_STANDALONE
+#define ELF_OSABI_EXACT 1
#define ELF_MAXPAGESIZE 1
#define TARGET_BIG_SYM visium_elf32_vec
diff --git a/bfd/elf64-alpha.c b/bfd/elf64-alpha.c
index 71b2cb4e57d..199505d17a5 100644
--- a/bfd/elf64-alpha.c
+++ b/bfd/elf64-alpha.c
@@ -5499,6 +5499,8 @@ static const struct elf_size_info alpha_elf_size_info =
#define TARGET_LITTLE_NAME "elf64-alpha-freebsd"
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_FREEBSD
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
/* The kernel recognizes executables as valid only if they carry a
"FreeBSD" label in the ELF header. So we put this label on all
diff --git a/bfd/elf64-hppa.c b/bfd/elf64-hppa.c
index d0bc3c33d68..2df62923ee5 100644
--- a/bfd/elf64-hppa.c
+++ b/bfd/elf64-hppa.c
@@ -4166,6 +4166,7 @@ static const struct elf_size_info hppa64_elf_size_info =
64M. But everything still uses 4k. */
#define ELF_MAXPAGESIZE 0x1000
#define ELF_OSABI ELFOSABI_HPUX
+#define ELF_OSABI_EXACT 1
#define bfd_elf64_bfd_reloc_type_lookup elf_hppa_reloc_type_lookup
#define bfd_elf64_bfd_reloc_name_lookup elf_hppa_reloc_name_lookup
diff --git a/bfd/elf64-ia64-vms.c b/bfd/elf64-ia64-vms.c
index bdd1b5b9753..4403688ec96 100644
--- a/bfd/elf64-ia64-vms.c
+++ b/bfd/elf64-ia64-vms.c
@@ -5568,6 +5568,8 @@ static const struct elf_size_info elf64_ia64_vms_size_info = {
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_OPENVMS
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
#undef ELF_MAXPAGESIZE
#define ELF_MAXPAGESIZE 0x10000 /* 64KB */
diff --git a/bfd/elf64-mips.c b/bfd/elf64-mips.c
index 26e3c602bba..8824214f18a 100644
--- a/bfd/elf64-mips.c
+++ b/bfd/elf64-mips.c
@@ -4868,6 +4868,8 @@ static const struct elf_size_info mips_elf64_size_info =
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_FREEBSD
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
#undef elf64_bed
#define elf64_bed elf64_fbsd_tradbed
diff --git a/bfd/elf64-ppc.c b/bfd/elf64-ppc.c
index be41efe10bd..7e41085ed91 100644
--- a/bfd/elf64-ppc.c
+++ b/bfd/elf64-ppc.c
@@ -18451,6 +18451,8 @@ ppc64_elf_free_cached_info (bfd *abfd)
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_FREEBSD
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
#undef elf64_bed
#define elf64_bed elf64_powerpc_fbsd_bed
diff --git a/bfd/elf64-sparc.c b/bfd/elf64-sparc.c
index 06c4e492ff8..cf0826f52b8 100644
--- a/bfd/elf64-sparc.c
+++ b/bfd/elf64-sparc.c
@@ -994,6 +994,8 @@ static const struct elf_size_info elf64_sparc_size_info =
#define TARGET_BIG_NAME "elf64-sparc-freebsd"
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_FREEBSD
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
#undef elf64_bed
#define elf64_bed elf64_sparc_fbsd_bed
@@ -1013,6 +1015,7 @@ static const struct elf_size_info elf64_sparc_size_info =
/* Restore default: we cannot use ELFOSABI_SOLARIS, otherwise ELFOSABI_NONE
objects won't be recognized. */
#undef ELF_OSABI
+#undef ELF_OSABI_EXACT
#undef elf64_bed
#define elf64_bed elf64_sparc_sol2_bed
diff --git a/bfd/elf64-x86-64.c b/bfd/elf64-x86-64.c
index 72a828a8c13..47d24e0e776 100644
--- a/bfd/elf64-x86-64.c
+++ b/bfd/elf64-x86-64.c
@@ -6426,6 +6426,8 @@ elf_x86_64_special_sections[]=
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_FREEBSD
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
#undef elf64_bed
#define elf64_bed elf64_x86_64_fbsd_bed
@@ -6448,6 +6450,7 @@ elf_x86_64_special_sections[]=
/* Restore default: we cannot use ELFOSABI_SOLARIS, otherwise ELFOSABI_NONE
objects won't be recognized. */
#undef ELF_OSABI
+#undef ELF_OSABI_EXACT
#undef elf64_bed
#define elf64_bed elf64_x86_64_sol2_bed
@@ -6468,6 +6471,7 @@ elf_x86_64_special_sections[]=
/* Restore defaults. */
#undef ELF_OSABI
+#undef ELF_OSABI_EXACT
#undef elf_backend_static_tls_alignment
#undef elf_backend_want_plt_sym
#define elf_backend_want_plt_sym 0
@@ -6489,6 +6493,7 @@ elf_x86_64_special_sections[]=
#undef ELF_TARGET_OS
#undef ELF_OSABI
+#undef ELF_OSABI_EXACT
#define bfd_elf32_bfd_copy_private_section_data \
elf_x86_64_copy_private_section_data
diff --git a/bfd/elfcode.h b/bfd/elfcode.h
index 3fde79c9c53..d7c82f0797c 100644
--- a/bfd/elfcode.h
+++ b/bfd/elfcode.h
@@ -628,9 +628,7 @@ elf_object_p (bfd *abfd)
goto got_no_match;
}
- if (ebd->elf_machine_code != EM_NONE
- && i_ehdrp->e_ident[EI_OSABI] != ebd->elf_osabi
- && ebd->elf_osabi != ELFOSABI_NONE)
+ if (ebd->osabi_exact && i_ehdrp->e_ident[EI_OSABI] != ebd->elf_osabi)
goto got_wrong_format_error;
if (i_ehdrp->e_shoff >= sizeof (x_ehdr))
diff --git a/bfd/elfcore.h b/bfd/elfcore.h
index c570479c2ac..7932faff287 100644
--- a/bfd/elfcore.h
+++ b/bfd/elfcore.h
@@ -152,9 +152,7 @@ elf_core_file_p (bfd *abfd)
&& ebd->elf_machine_code != EM_NONE)
goto wrong;
- if (ebd->elf_machine_code != EM_NONE
- && i_ehdrp->e_ident[EI_OSABI] != ebd->elf_osabi
- && ebd->elf_osabi != ELFOSABI_NONE)
+ if (ebd->osabi_exact && i_ehdrp->e_ident[EI_OSABI] != ebd->elf_osabi)
goto wrong;
/* If there is no program header, or the type is not a core file, then
diff --git a/bfd/elfn32-mips.c b/bfd/elfn32-mips.c
index 97c859f7d25..a23333765a6 100644
--- a/bfd/elfn32-mips.c
+++ b/bfd/elfn32-mips.c
@@ -4254,6 +4254,8 @@ static const struct ecoff_debug_swap mips_elf32_ecoff_debug_swap = {
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_FREEBSD
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
#undef elf32_bed
#define elf32_bed elf32_fbsd_tradbed
diff --git a/bfd/elfnn-ia64.c b/bfd/elfnn-ia64.c
index fd1ac180b06..03a31f41beb 100644
--- a/bfd/elfnn-ia64.c
+++ b/bfd/elfnn-ia64.c
@@ -5108,6 +5108,8 @@ ignore_errors (const char *fmt ATTRIBUTE_UNUSED, ...)
#undef ELF_COMMONPAGESIZE
#undef ELF_OSABI
#define ELF_OSABI ELFOSABI_HPUX
+#undef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 1
#undef elfNN_bed
#define elfNN_bed elfNN_ia64_hpux_bed
diff --git a/bfd/elfxx-target.h b/bfd/elfxx-target.h
index 88f8a041ea8..48fb3082e8e 100644
--- a/bfd/elfxx-target.h
+++ b/bfd/elfxx-target.h
@@ -368,6 +368,10 @@
#define ELF_OSABI ELFOSABI_NONE
#endif
+#ifndef ELF_OSABI_EXACT
+#define ELF_OSABI_EXACT 0
+#endif
+
#ifndef ELF_MAXPAGESIZE
# error ELF_MAXPAGESIZE is not defined
#define ELF_MAXPAGESIZE 1
@@ -799,7 +803,9 @@
#ifndef elf_match_priority
#define elf_match_priority \
- (ELF_ARCH == bfd_arch_unknown ? 2 : ELF_OSABI == ELFOSABI_NONE ? 1 : 0)
+ (ELF_ARCH == bfd_arch_unknown ? 2 \
+ : ELF_OSABI == ELFOSABI_NONE || !ELF_OSABI_EXACT ? 1 \
+ : 0)
#endif
extern const struct elf_size_info _bfd_elfNN_size_info ATTRIBUTE_HIDDEN;
@@ -811,6 +817,7 @@ static const struct elf_backend_data elfNN_bed =
ELF_MACHINE_CODE,
ELF_TARGET_ID,
ELF_TARGET_OS,
+ ELF_OSABI_EXACT,
ELF_MAXPAGESIZE,
ELF_MINPAGESIZE,
ELF_COMMONPAGESIZE,
More information about the Binutils-cvs
mailing list