This is the mail archive of the binutils@sources.redhat.com 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]

Re: 2.15 branch merge


On Apr 20, 2004, Daniel Jacobowitz <drow@false.org> wrote:

> On Fri, Apr 16, 2004 at 05:31:13AM -0300, Alexandre Oliva wrote:
>> I also noticed that the non-PCREL exception handling patch is missing
>> from the 2.15 branch.  This means FDPIC is pretty much broken, at
>> least for C++, so there's little point in even trying to fix it in the
>> branch.  I attach a patch for the branch anyway, after the patch for
>> mainline.  They're equivalent except for the changes to the EH-related
>> functions that didn't exist in the branch.

> I don't much care what you do to the FRV specific files on the branch -
> the FRV port is not in wide use yet and the changes to other files are
> very simple.  So go ahead if it's approved for HEAD.

Ok, I'm checking this in, merged this from mainline.

Index: bfd/ChangeLog
from  Alexandre Oliva  <aoliva@redhat.com>

	Merge from mainline:
	2004-02-27  Alexandre Oliva  <aoliva@redhat.com>
	* elf-bfd.h (struct elf_backend_data): Added
	elf_backend_can_make_relative_eh_frame,
	elf_backend_can_make_lsda_relative_eh_frame and
	elf_backend_encode_eh_address.
	(_bfd_elf_encode_eh_address): Declare.
	(_bfd_elf_can_make_relative): Declare.
	* elf-eh-frame.c (_bfd_elf_discard_section_eh_frame): Use new
	hooks to decide whether to attempt to make_relative and
	make_lsda_relative.
	(_bfd_elf_write_section_eh_frame_hdr): Call encode_eh_address.
	(_bfd_elf_can_make_relative): New.
	(_bfd_elf_encode_eh_address): New.
	* elf32-frv.c (frv_elf_use_relative_eh_frame): New.
	(frv_elf_encode_eh_address): New.
	(elf_backend_can_make_relative_eh_frame): Define.
	(elf_backend_can_make_lsda_relative_eh_frame): Define.
	(elf_backend_encode_eh_address): Define.
	* elfxx-target.h
	(elf_backend_can_make_relative_eh_frame): Define.
	(elf_backend_can_make_lsda_relative_eh_frame): Define.
	(elf_backend_encode_eh_address): Define.
	(elfNN_bed): Add them.

Index: bfd/elf-bfd.h
===================================================================
RCS file: /cvs/src/src/bfd/elf-bfd.h,v
retrieving revision 1.125.4.1
diff -u -p -r1.125.4.1 elf-bfd.h
--- bfd/elf-bfd.h 8 Apr 2004 12:41:35 -0000 1.125.4.1
+++ bfd/elf-bfd.h 6 May 2004 01:53:10 -0000
@@ -861,6 +861,24 @@ struct elf_backend_data
   bfd_boolean (*elf_backend_ignore_discarded_relocs)
     (asection *);
 
+  /* These functions tell elf-eh-frame whether to attempt to turn
+     absolute or lsda encodings into pc-relative ones.  The default
+     definition enables these transformations.  */
+  bfd_boolean (*elf_backend_can_make_relative_eh_frame)
+     (bfd *, struct bfd_link_info *, asection *);
+  bfd_boolean (*elf_backend_can_make_lsda_relative_eh_frame)
+     (bfd *, struct bfd_link_info *, asection *);
+
+  /* This function returns an encoding after computing the encoded
+     value (and storing it in ENCODED) for the given OFFSET into OSEC,
+     to be stored in at LOC_OFFSET into the LOC_SEC input section.
+     The default definition chooses a 32-bit PC-relative encoding.  */
+  bfd_byte (*elf_backend_encode_eh_address)
+     (bfd *abfd, struct bfd_link_info *info,
+      asection *osec, bfd_vma offset,
+      asection *loc_sec, bfd_vma loc_offset,
+      bfd_vma *encoded);
+
   /* This function, if defined, may write out the given section.
      Returns TRUE if it did so and FALSE if the caller should.  */
   bfd_boolean (*elf_backend_write_section)
@@ -1295,6 +1313,12 @@ extern void _bfd_elf_sprintf_vma
   (bfd *, char *, bfd_vma);
 extern void _bfd_elf_fprintf_vma
   (bfd *, void *, bfd_vma);
+
+extern bfd_byte _bfd_elf_encode_eh_address
+  (bfd *abfd, struct bfd_link_info *info, asection *osec, bfd_vma offset,
+   asection *loc_sec, bfd_vma loc_offset, bfd_vma *encoded);
+extern bfd_boolean _bfd_elf_can_make_relative
+  (bfd *input_bfd, struct bfd_link_info *info, asection *eh_frame_section);
 
 extern enum elf_reloc_type_class _bfd_elf_reloc_type_class
   (const Elf_Internal_Rela *);
Index: bfd/elf-eh-frame.c
===================================================================
RCS file: /cvs/src/src/bfd/elf-eh-frame.c,v
retrieving revision 1.27
diff -u -p -r1.27 elf-eh-frame.c
--- bfd/elf-eh-frame.c 16 Oct 2003 21:04:04 -0000 1.27
+++ bfd/elf-eh-frame.c 6 May 2004 01:53:11 -0000
@@ -518,10 +518,16 @@ _bfd_elf_discard_section_eh_frame
 	  /* For shared libraries, try to get rid of as many RELATIVE relocs
 	     as possible.  */
           if (info->shared
+	      && (get_elf_backend_data (abfd)
+		  ->elf_backend_can_make_relative_eh_frame
+		  (abfd, info, sec))
 	      && (cie.fde_encoding & 0xf0) == DW_EH_PE_absptr)
 	    cie.make_relative = 1;
 
 	  if (info->shared
+	      && (get_elf_backend_data (abfd)
+		  ->elf_backend_can_make_lsda_relative_eh_frame
+		  (abfd, info, sec))
 	      && (cie.lsda_encoding & 0xf0) == DW_EH_PE_absptr)
 	    cie.make_lsda_relative = 1;
 
@@ -1120,6 +1126,7 @@ _bfd_elf_write_section_eh_frame_hdr (bfd
   asection *eh_frame_sec;
   bfd_size_type size;
   bfd_boolean retval;
+  bfd_vma encoded_eh_frame;
 
   htab = elf_hash_table (info);
   hdr_info = &htab->eh_info;
@@ -1143,7 +1150,10 @@ _bfd_elf_write_section_eh_frame_hdr (bfd
 
   memset (contents, 0, EH_FRAME_HDR_SIZE);
   contents[0] = 1;				/* Version.  */
-  contents[1] = DW_EH_PE_pcrel | DW_EH_PE_sdata4; /* .eh_frame offset.  */
+  contents[1] = get_elf_backend_data (abfd)->elf_backend_encode_eh_address
+    (abfd, info, eh_frame_sec, 0, sec, 4,
+     &encoded_eh_frame);			/* .eh_frame offset.  */
+
   if (hdr_info->array && hdr_info->array_count == hdr_info->fde_count)
     {
       contents[2] = DW_EH_PE_udata4;		/* FDE count encoding.  */
@@ -1154,8 +1164,8 @@ _bfd_elf_write_section_eh_frame_hdr (bfd
       contents[2] = DW_EH_PE_omit;
       contents[3] = DW_EH_PE_omit;
     }
-  bfd_put_32 (abfd, eh_frame_sec->vma - sec->output_section->vma - 4,
-	      contents + 4);
+  bfd_put_32 (abfd, encoded_eh_frame, contents + 4);
+
   if (contents[2] != DW_EH_PE_omit)
     {
       unsigned int i;
@@ -1180,4 +1190,30 @@ _bfd_elf_write_section_eh_frame_hdr (bfd
 				     sec->_cooked_size);
   free (contents);
   return retval;
+}
+
+/* Decide whether we can use a PC-relative encoding within the given
+   EH frame section.  This is the default implementation.  */
+
+bfd_boolean
+_bfd_elf_can_make_relative (bfd *input_bfd ATTRIBUTE_UNUSED,
+			    struct bfd_link_info *info ATTRIBUTE_UNUSED,
+			    asection *eh_frame_section ATTRIBUTE_UNUSED)
+{
+  return TRUE;
+}
+
+/* Select an encoding for the given address.  Preference is given to
+   PC-relative addressing modes.  */
+
+bfd_byte
+_bfd_elf_encode_eh_address (bfd *abfd ATTRIBUTE_UNUSED,
+			    struct bfd_link_info *info ATTRIBUTE_UNUSED,
+			    asection *osec, bfd_vma offset,
+			    asection *loc_sec, bfd_vma loc_offset,
+			    bfd_vma *encoded)
+{
+  *encoded = osec->vma + offset -
+    (loc_sec->output_section->vma + loc_sec->output_offset + loc_offset);
+  return DW_EH_PE_pcrel | DW_EH_PE_sdata4;
 }
Index: bfd/elf32-frv.c
===================================================================
RCS file: /cvs/src/src/bfd/elf32-frv.c,v
retrieving revision 1.12.4.2
diff -u -p -r1.12.4.2 elf32-frv.c
--- bfd/elf32-frv.c 9 Apr 2004 18:28:00 -0000 1.12.4.2
+++ bfd/elf32-frv.c 6 May 2004 01:53:14 -0000
@@ -22,6 +22,7 @@ Foundation, Inc., 59 Temple Place - Suit
 #include "libbfd.h"
 #include "elf-bfd.h"
 #include "elf/frv.h"
+#include "elf/dwarf2.h"
 #include "hashtab.h"
 
 /* Forward declarations.  */
@@ -3803,6 +3804,57 @@ elf32_frv_finish_dynamic_symbol (bfd *ou
   return TRUE;
 }
 
+/* Decide whether to attempt to turn absptr or lsda encodings in
+   shared libraries into pcrel within the given input section.  */
+
+static bfd_boolean
+frv_elf_use_relative_eh_frame (bfd *input_bfd,
+			       struct bfd_link_info *info ATTRIBUTE_UNUSED,
+			       asection *eh_frame_section ATTRIBUTE_UNUSED)
+{
+  /* We can't use PC-relative encodings in FDPIC binaries, in general.  */
+  if (elf_elfheader (input_bfd)->e_flags & EF_FRV_FDPIC)
+    return FALSE;
+
+  return TRUE;
+}
+
+/* Adjust the contents of an eh_frame_hdr section before they're output.  */
+
+static bfd_byte
+frv_elf_encode_eh_address (bfd *abfd,
+			   struct bfd_link_info *info,
+			   asection *osec, bfd_vma offset,
+			   asection *loc_sec, bfd_vma loc_offset,
+			   bfd_vma *encoded)
+{
+  struct elf_link_hash_entry *h;
+
+  /* Non-FDPIC binaries can use PC-relative encodings.  */
+  if (! (elf_elfheader (abfd)->e_flags & EF_FRV_FDPIC))
+    return _bfd_elf_encode_eh_address (abfd, info, osec, offset,
+				       loc_sec, loc_offset, encoded);
+
+  h = elf_hash_table (info)->hgot;
+  BFD_ASSERT (h && h->root.type == bfd_link_hash_defined);
+
+  if (! h || (_frv_osec_to_segment (abfd, osec)
+	      == _frv_osec_to_segment (abfd, loc_sec->output_section)))
+    return _bfd_elf_encode_eh_address (abfd, info, osec, offset,
+				       loc_sec, loc_offset, encoded);
+
+  BFD_ASSERT (_frv_osec_to_segment (abfd, osec)
+	      == _frv_osec_to_segment (abfd,
+				       h->root.u.def.section->output_section));
+
+  *encoded = osec->vma + offset
+    - (h->root.u.def.value
+       + h->root.u.def.section->output_section->vma
+       + h->root.u.def.section->output_offset);
+
+  return DW_EH_PE_datarel | DW_EH_PE_sdata4;
+}
+
 /* Look through the relocs for a section during the first phase.
 
    Besides handling virtual table relocs for gc, we have to deal with
@@ -4521,6 +4573,12 @@ frv_elf_print_private_bfd_data (abfd, pt
 #define elf_backend_plt_readonly	1
 #define elf_backend_want_plt_sym	0
 #define elf_backend_plt_header_size	0
+
+#define elf_backend_can_make_relative_eh_frame \
+		frv_elf_use_relative_eh_frame
+#define elf_backend_can_make_lsda_relative_eh_frame \
+		frv_elf_use_relative_eh_frame
+#define elf_backend_encode_eh_address	frv_elf_encode_eh_address
 
 #define elf_backend_may_use_rel_p       1
 #define elf_backend_may_use_rela_p      1
Index: bfd/elfxx-target.h
===================================================================
RCS file: /cvs/src/src/bfd/elfxx-target.h,v
retrieving revision 1.59.4.1
diff -u -p -r1.59.4.1 elfxx-target.h
--- bfd/elfxx-target.h 8 Apr 2004 12:41:46 -0000 1.59.4.1
+++ bfd/elfxx-target.h 6 May 2004 01:53:14 -0000
@@ -401,6 +401,15 @@
 #ifndef elf_backend_ignore_discarded_relocs
 #define elf_backend_ignore_discarded_relocs	NULL
 #endif
+#ifndef elf_backend_can_make_relative_eh_frame
+#define elf_backend_can_make_relative_eh_frame	_bfd_elf_can_make_relative
+#endif
+#ifndef elf_backend_can_make_lsda_relative_eh_frame
+#define elf_backend_can_make_lsda_relative_eh_frame	_bfd_elf_can_make_relative
+#endif
+#ifndef elf_backend_encode_eh_address
+#define elf_backend_encode_eh_address		_bfd_elf_encode_eh_address
+#endif
 #ifndef elf_backend_write_section
 #define elf_backend_write_section		NULL
 #endif
@@ -507,6 +516,9 @@ static const struct elf_backend_data elf
   elf_backend_reloc_type_class,
   elf_backend_discard_info,
   elf_backend_ignore_discarded_relocs,
+  elf_backend_can_make_relative_eh_frame,
+  elf_backend_can_make_lsda_relative_eh_frame,
+  elf_backend_encode_eh_address,
   elf_backend_write_section,
   elf_backend_mips_irix_compat,
   elf_backend_mips_rtype_to_howto,
-- 
Alexandre Oliva             http://www.ic.unicamp.br/~oliva/
Red Hat Compiler Engineer   aoliva@{redhat.com, gcc.gnu.org}
Free Software Evangelist  oliva@{lsd.ic.unicamp.br, gnu.org}

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