This is the mail archive of the binutils@sourceware.org mailing list for the binutils project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

bfd_arch_get_compatible


Some time ago --accept-unknown-input-format was added to ld,
http://sourceware.org/ml/binutils/2002-12/msg00517.html but the patch
committed differed from the posted patch, and had an error.  As far as
I can tell the error would never be noticed, since the return value of
bfd_arch_get_compatible is only tested for non-NULL, except in one
place.  That place, elf32_m68k_merge_private_bfd_data, doesn't allow
binary or unknown architectures, so the buggy return value doesn't
matter there either.  Fixed by the following archures.c patch.

Incidentally, the reason I happened to be looking at this code is
because --accept-unknown-input-format has quite weird behaviour.  For
example, suppose you build a powerpc-linux ld just using the default
configure options, then --accept-unknown-input-format lets you link in
i686-linux object files.  However, if you build powerpc-linux ld with
--enable-targets=all, then you can't link in i686-linux objects.  So
--enable-targets=all in this case gives you *less* functionality.

In fact, you can't even do it by forcing the generic ELF target for
the x86 objects with -b, hence the elfcode.h patch.

	* archures.c (bfd_arch_get_compatible): If one arch is unknown,
	return the other arch.
	* elfcode.h (elf_object_p): Allow explicit match to generic ELF
	target.

Index: bfd/archures.c
===================================================================
RCS file: /cvs/src/src/bfd/archures.c,v
retrieving revision 1.153
diff -u -p -r1.153 archures.c
--- bfd/archures.c	22 Mar 2011 18:10:41 -0000	1.153
+++ bfd/archures.c	3 Jun 2011 06:12:50 -0000
@@ -1,6 +1,6 @@
 /* BFD library support routines for architectures.
    Copyright 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999,
-   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010
+   2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011
    Free Software Foundation, Inc.
    Hacked by John Gilmore and Steve Chamberlain of Cygnus Support.
 
@@ -748,25 +748,26 @@ bfd_arch_get_compatible (const bfd *abfd
 			 const bfd *bbfd,
 			 bfd_boolean accept_unknowns)
 {
-  const bfd * ubfd = NULL;
+  const bfd *ubfd, *kbfd;
 
   /* Look for an unknown architecture.  */
-  if (((ubfd = abfd) && ubfd->arch_info->arch == bfd_arch_unknown)
-      || ((ubfd = bbfd) && ubfd->arch_info->arch == bfd_arch_unknown))
-    {
-      /* We can allow an unknown architecture if accept_unknowns
-	 is true, or if the target is the "binary" format, which
-	 has an unknown architecture.  Since the binary format can
-	 only be set by explicit request from the user, it is safe
-	 to assume that they know what they are doing.  */
-      if (accept_unknowns
-	  || strcmp (bfd_get_target (ubfd), "binary") == 0)
-	return ubfd->arch_info;
-      return NULL;
-    }
-
-  /* Otherwise architecture-specific code has to decide.  */
-  return abfd->arch_info->compatible (abfd->arch_info, bbfd->arch_info);
+  if (abfd->arch_info->arch == bfd_arch_unknown)
+    ubfd = abfd, kbfd = bbfd;
+  else if (bbfd->arch_info->arch == bfd_arch_unknown)
+    ubfd = bbfd, kbfd = abfd;
+  else
+    /* Otherwise architecture-specific code has to decide.  */
+    return abfd->arch_info->compatible (abfd->arch_info, bbfd->arch_info);
+
+  /* We can allow an unknown architecture if accept_unknowns
+     is true, or if the target is the "binary" format, which
+     has an unknown architecture.  Since the binary format can
+     only be set by explicit request from the user, it is safe
+     to assume that they know what they are doing.  */
+  if (accept_unknowns
+      || strcmp (bfd_get_target (ubfd), "binary") == 0)
+    return kbfd->arch_info;
+  return NULL;
 }
 
 /*
Index: bfd/elfcode.h
===================================================================
RCS file: /cvs/src/src/bfd/elfcode.h,v
retrieving revision 1.106
diff -u -p -r1.106 elfcode.h
--- bfd/elfcode.h	20 Apr 2011 00:22:08 -0000	1.106
+++ bfd/elfcode.h	4 Jun 2011 03:22:32 -0000
@@ -595,26 +595,27 @@ elf_object_p (bfd *abfd)
 
       /* This is the generic ELF target.  Let it match any ELF target
 	 for which we do not have a specific backend.  */
-      for (target_ptr = bfd_target_vector; *target_ptr != NULL; target_ptr++)
-	{
-	  const struct elf_backend_data *back;
+      if (abfd->target_defaulted)
+	for (target_ptr = bfd_target_vector; *target_ptr != NULL; target_ptr++)
+	  {
+	    const struct elf_backend_data *back;
 
-	  if ((*target_ptr)->flavour != bfd_target_elf_flavour)
-	    continue;
-	  back = xvec_get_elf_backend_data (*target_ptr);
-	  if (back->s->arch_size != ARCH_SIZE)
-	    continue;
-	  if (back->elf_machine_code == i_ehdrp->e_machine
-	      || (back->elf_machine_alt1 != 0
-		  && back->elf_machine_alt1 == i_ehdrp->e_machine)
-	      || (back->elf_machine_alt2 != 0
-		  && back->elf_machine_alt2 == i_ehdrp->e_machine))
-	    {
-	      /* target_ptr is an ELF backend which matches this
-		 object file, so reject the generic ELF target.  */
-	      goto got_wrong_format_error;
-	    }
-	}
+	    if ((*target_ptr)->flavour != bfd_target_elf_flavour)
+	      continue;
+	    back = xvec_get_elf_backend_data (*target_ptr);
+	    if (back->s->arch_size != ARCH_SIZE)
+	      continue;
+	    if (back->elf_machine_code == i_ehdrp->e_machine
+		|| (back->elf_machine_alt1 != 0
+		    && back->elf_machine_alt1 == i_ehdrp->e_machine)
+		|| (back->elf_machine_alt2 != 0
+		    && back->elf_machine_alt2 == i_ehdrp->e_machine))
+	      {
+		/* target_ptr is an ELF backend which matches this
+		   object file, so reject the generic ELF target.  */
+		goto got_wrong_format_error;
+	      }
+	  }
     }
 
   if (i_ehdrp->e_type == ET_EXEC)

-- 
Alan Modra
Australia Development Lab, IBM


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]