Fixing plt generation on powerpc-vxworks

Richard Sandiford richard@codesourcery.com
Wed Mar 1 17:18:00 GMT 2006


The powerpc-vxworks port seems to have bitrotted slightly in the time
since it was submitted.  I realise that this was inevitable given that
(a) there are no VxWorks testcases and (b) there has been no regular
testing on a VxWorks system.  I can't promise to do anything about (b),
but this patch should at least help a little with (a).

The main souce of bitrot is that VxWorks has its own PLT layout, so the
choice between the "old" and "new" standard layouts is not meaningful.
On the one hand, the VxWorks handling in elf32-ppc.c can (and does)
share code with the "old_plt" case.  On the other, VxWorks .plts are
read-only executable sections, just like new .plts are.  They should
therefore go in the text segment rather than the data segment.

The first order problem is that ppc_elf_select_plt_layout ends up setting
"old_plt" for VxWorks, and thus returns 0.  This causes the linker to
pick the second .plt section statement, i.e. the one for the data segment.

I'll return to the "old_plt"/"new_plt" vs. "is_vxworks" thing below.
First of all though, the generic ELF handling of GOT and PLT is correct
for VxWorks, so we don't need the special old/new handling in elf32ppc.sh.
We also don't want the associated command-line support in ppc32.em.

I wondered about three ways of dealing with this:

  (a) Getting elf32ppcvxworks.sh to undefine all the stuff in
      elf32ppc.sh that we don't want.

  (b) Removing the include of elf32ppc.sh in elf32ppcvxworks.sh
      and cut-&-pasting all the bits we _do_ need.

  (c) Syphoning off the non-PLT parts of elf32ppc.sh into a new file.

I don't like (a) because it's harder to tell what's left and I don't
like (b) because of the code duplication.  I therefore went for (c).

The question is then whether powerpc-vxworks should still call
ppc_elf_select_plt_layout.  That in turn raises the question:
what does "old_plt" mean on VxWorks after ppc_elf_select_plt_layout
has been called?

The answer to the second question isn't entirely clear at the moment.
If I've understood correctly, "old_plt" means "must use the old layout"
and "new_plt" means "try to use the new layout".  The choice is finalised
by ppc_elf_select_plt_layout, which sets "old_plt" if "!new_plt"
or "force_old_plt" is set.  All later code uses "old_plt" exclusively.

At the moment, some VxWorks-sensitive parts of elf32-ppc.c are conditional
on "old_plt || is_vxworks", which implies that the setting of "old_plt"
shouldn't matter for VxWorks.  However, other parts use "old_plt" to guard
code that should be used for both the old and VxWorks layouts.  An example
from ppc_elf_relocate_section is:

	    unresolved_reloc = FALSE;
	    if (!htab->old_plt)
	      relocation = (htab->glink->output_section->vma
			    + htab->glink->output_offset
			    + ent->glink_offset);
	    else
	      relocation = (htab->plt->output_section->vma
			    + htab->plt->output_offset
			    + ent->plt.offset);

where we want the "else" version for VxWorks.  Because of this,
the current code implicitly requires "old_plt" to be set for VxWorks,
which in turn makes the "is_vxworks" part of "old_plt || is_vxworks"
redundant.

As a much more minor point, the "old_plt" vs. "new_plt" stuff in
ppc_elf_check_relocs isn't meaningful on VxWorks: we only have one
choice of PLT there.

To avoid this sort of issue, I thought it would be cleaner if we had an
explicit three-way choice: old, new or vxworks.  The patch therefore
replaces "old_plt" and "new_plt" with two new fields:

    plt_type = PLT_UNSET | PLT_OLD | PLT_NEW | PLT_VXWORKS
    can_use_new_plt

The latter is a direct replacement for "new_plt".  The former starts
off as PLT_UNSET, but once it is changed to something else, that choice
is set in stone.

Because there's only one possible choice on VxWorks, we can move from
PLT_UNSET to PLT_VXWORKS as early as ppc_elf_vxworks_link_hash_table_create.
On non-VxWorks targets, ppc_elf_check_relocs can move from PLT_UNSET to
PLT_OLD in cases where it used to set old_plt ("must use the old layout").
Finally, ppc_elf_select_plt_layout moves from PLT_UNSET to PLT_OLD or
PLT_NEW depending on the settings of "force_old_plt" and "can_use_new_plt".

Tested on powerpc-vxworks, powerpc64-linux-gnu and i686-pc-linux-gnu
(--enable-targets=all --enable-64-bit-bfd).  OK to install?

Richard


bfd/
	* elf32-ppc.c (ppc_elf_plt_type): New enumeration.
	(ppc_elf_link_hash_table): Replace old_got and new_got with
	plt_type and can_use_new_plt.
	(ppc_elf_create_dynamic_sections): Add SEC_HAS_CONTENTS,
	SEC_LOAD and SEC_READONLY to the VxWorks .plt flags.
	(ppc_elf_check_relocs): Set can_use_new_plt instead of new_plt.
	Move from plt_type == PLT_UNSET to PLT_OLD instead of setting old_plt.
	(ppc_elf_select_plt_layout): Move from plt_type == PLT_UNSET to
	either plt_type == PLT_OLD or plt_type == PLT_NEW.  Assert that
	this function should not be called for VxWorks targets.
	(ppc_elf_tls_setup): Use plt_type instead of old_got.
	(allocate_got): Likewise.  Rearrange so that max_before_header
	is only used for PLT_OLD and PLT_NEW.
	(allocate_dynrelocs): Use plt_type instead of old_got and is_vxworks.
	(ppc_elf_size_dynamic_sections): Likewise.
	(ppc_elf_relax_section): Likewise.
	(ppc_elf_relocate_section): Likewise.
	(ppc_elf_finish_dynamic_symbol): Likewise.
	(ppc_elf_vxworks_link_hash_table_create): Initialize plt_type.

ld/
	* emulparams/elf32ppccommon.sh: New file, extracted from...
	* emulparams/elf32ppc.sh: ...here.
	* emulparams/elf32ppcvxworks.sh: Include elf32ppccommon.sh
	instead of elf32ppc.sh.
	(BSS_PLT): Remove override.
	* Makefile.am (eelf32lppc.c): Depend on elf32ppccommons.h.
	(eelf32lppcnto.c, eelf32lppcsim.c, eelf32ppcnto.c): Likewise.
	(eelf32ppc.c, eelf32ppc_fbsd.c, eelf32ppcsimm): Likewise.
	(eelf32ppclinux.c): Likewise.
	(eelf32ppcvxworks.c): Likewise.  Add missing vxworks.sh dependency.
	* Makefile.in: Regenerate.

ld/testsuite/
	* ld-powerpc/vxworks1-lib.s, ld-powerpc/vxworks1-lib.dd,
	* ld-powerpc/vxworks1-lib.rd, ld-powerpc/vxworks1.s,
	* ld-powerpc/vxworks1.dd, ld-powerpc/vxworks1.rd,
	* ld-powerpc/vxworks1.ld, ld-powerpc/vxworks1.sd: New test.
	* ld-powerpc/powerpc.exp: Run it.

diff -uprN ../src.1/bfd/elf32-ppc.c ./bfd/elf32-ppc.c
--- ./bfd/elf32-ppc.c	2006-02-25 09:38:20.000000000 +0000
+++ ./bfd/elf32-ppc.c	2006-03-01 16:25:44.000000000 +0000
@@ -2313,6 +2313,13 @@ struct ppc_elf_link_hash_entry
 
 #define ppc_elf_hash_entry(ent) ((struct ppc_elf_link_hash_entry *) (ent))
 
+enum ppc_elf_plt_type {
+  PLT_UNSET,
+  PLT_OLD,
+  PLT_NEW,
+  PLT_VXWORKS
+};
+
 /* PPC ELF linker hash table.  */
 
 struct ppc_elf_link_hash_table
@@ -2349,9 +2356,11 @@ struct ppc_elf_link_hash_table
   /* Non-zero if allocating the header left a gap.  */
   unsigned int got_gap;
 
-  /* Whether to use new plt/got layout or not.  */
-  unsigned int new_plt:1;
-  unsigned int old_plt:1;
+  /* The type of PLT we have chosen to use.  */
+  enum ppc_elf_plt_type plt_type;
+
+  /* Whether we can use the new PLT layout.  */
+  unsigned int can_use_new_plt:1;
 
   /* Set if we should emit symbols for stubs.  */
   unsigned int emit_stub_syms:1;
@@ -2559,6 +2568,9 @@ ppc_elf_create_dynamic_sections (bfd *ab
     abort ();
 
   flags = SEC_ALLOC | SEC_CODE | SEC_LINKER_CREATED;
+  if (htab->plt_type == PLT_VXWORKS)
+    /* The VxWorks PLT is a loaded section with contents.  */
+    flags |= SEC_HAS_CONTENTS | SEC_LOAD | SEC_READONLY;
   return bfd_set_section_flags (abfd, s, flags);
 }
 
@@ -3245,7 +3257,7 @@ ppc_elf_check_relocs (bfd *abfd,
 	case R_PPC_REL16_LO:
 	case R_PPC_REL16_HI:
 	case R_PPC_REL16_HA:
-	  htab->new_plt = 1;
+	  htab->can_use_new_plt = 1;
 	  break;
 
 	  /* These are just markers.  */
@@ -3273,8 +3285,8 @@ ppc_elf_check_relocs (bfd *abfd,
 
 	  /* This refers only to functions defined in the shared library.  */
 	case R_PPC_LOCAL24PC:
-	  if (h && h == htab->elf.hgot)
-	    htab->old_plt = 1;
+	  if (h && h == htab->elf.hgot && htab->plt_type == PLT_UNSET)
+	    htab->plt_type = PLT_OLD;
 	  break;
 
 	  /* This relocation describes the C++ object vtable hierarchy.
@@ -3315,7 +3327,7 @@ ppc_elf_check_relocs (bfd *abfd,
 	      && got2 != NULL
 	      && (sec->flags & SEC_CODE) != 0
 	      && (info->shared || info->pie)
-	      && !htab->old_plt)
+	      && htab->plt_type == PLT_UNSET)
 	    {
 	      /* Old -fPIC gcc code has .long LCTOC1-LCFx just before
 		 the start of a function, which assembles to a REL32
@@ -3328,7 +3340,7 @@ ppc_elf_check_relocs (bfd *abfd,
 	      s = bfd_section_from_r_symndx (abfd, &htab->sym_sec, sec,
 					     r_symndx);
 	      if (s == got2)
-		htab->old_plt = 1;
+		htab->plt_type = PLT_OLD;
 	    }
 	  /* fall through */
 
@@ -3338,9 +3350,9 @@ ppc_elf_check_relocs (bfd *abfd,
 	case R_PPC_REL14_BRNTAKEN:
 	  if (h == NULL)
 	    break;
-	  if (h == htab->elf.hgot)
+	  if (h == htab->elf.hgot && htab->plt_type == PLT_UNSET)
 	    {
-	      htab->old_plt = 1;
+	      htab->plt_type = PLT_OLD;
 	      break;
 	    }
 	  /* fall through */
@@ -3600,22 +3612,16 @@ ppc_elf_select_plt_layout (bfd *output_b
   flagword flags;
 
   htab = ppc_elf_hash_table (info);
-  if (force_old_plt || !htab->new_plt)
-    htab->old_plt = 1;
+
+  if (htab->plt_type == PLT_UNSET)
+    htab->plt_type = (force_old_plt || !htab->can_use_new_plt
+		      ? PLT_OLD : PLT_NEW);
 
   htab->emit_stub_syms = emit_stub_syms;
 
-  if (htab->is_vxworks)
-    {
-      /* The VxWorks PLT is a loaded section with contents.  */
-      flags = SEC_ALLOC | SEC_CODE | SEC_IN_MEMORY | SEC_LINKER_CREATED
-	      | SEC_HAS_CONTENTS | SEC_LOAD | SEC_READONLY;
+  BFD_ASSERT (htab->plt_type != PLT_VXWORKS);
 
-      if (htab->plt != NULL
-	  && !bfd_set_section_flags (htab->elf.dynobj, htab->plt, flags))
-	return -1;
-    }
-  else if (!htab->old_plt)
+  if (htab->plt_type == PLT_NEW)
     {
       flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS
 	       | SEC_IN_MEMORY | SEC_LINKER_CREATED);
@@ -3637,7 +3643,7 @@ ppc_elf_select_plt_layout (bfd *output_b
 	  && !bfd_set_section_alignment (htab->elf.dynobj, htab->glink, 0))
 	return -1;
     }
-  return !htab->old_plt;
+  return htab->plt_type == PLT_NEW;
 }
 
 /* Return the section that should be marked against GC for a given
@@ -3825,7 +3831,7 @@ ppc_elf_tls_setup (bfd *obfd, struct bfd
   struct ppc_elf_link_hash_table *htab;
 
   htab = ppc_elf_hash_table (info);
-  if (!htab->old_plt
+  if (htab->plt_type == PLT_NEW
       && htab->plt != NULL
       && htab->plt->output_section != NULL)
     {
@@ -4269,31 +4275,32 @@ static bfd_vma
 allocate_got (struct ppc_elf_link_hash_table *htab, unsigned int need)
 {
   bfd_vma where;
-  unsigned int max_before_header = 32768;
-
-  if (htab->old_plt)
-    max_before_header = 32764;
+  unsigned int max_before_header;
 
-  if (htab->is_vxworks)
+  if (htab->plt_type == PLT_VXWORKS)
     {
       where = htab->got->size;
       htab->got->size += need;
     }
-  else if (need <= htab->got_gap)
-    {
-      where = max_before_header - htab->got_gap;
-      htab->got_gap -= need;
-    }
   else
     {
-      if (htab->got->size + need > max_before_header
-	  && htab->got->size <= max_before_header)
+      max_before_header = htab->plt_type == PLT_NEW ? 32768 : 32764;
+      if (need <= htab->got_gap)
 	{
-	  htab->got_gap = max_before_header - htab->got->size;
-	  htab->got->size = max_before_header + htab->got_header_size;
+	  where = max_before_header - htab->got_gap;
+	  htab->got_gap -= need;
+	}
+      else
+	{
+	  if (htab->got->size + need > max_before_header
+	      && htab->got->size <= max_before_header)
+	    {
+	      htab->got_gap = max_before_header - htab->got->size;
+	      htab->got->size = max_before_header + htab->got_header_size;
+	    }
+	  where = htab->got->size;
+	  htab->got->size += need;
 	}
-      where = htab->got->size;
-      htab->got->size += need;
     }
   return where;
 }
@@ -4340,7 +4347,7 @@ allocate_dynrelocs (struct elf_link_hash
 	      {
 		asection *s = htab->plt;
 
-		if (!(htab->old_plt || htab->is_vxworks))
+		if (htab->plt_type == PLT_NEW)
 		  {
 		    if (!doneone)
 		      {
@@ -4404,7 +4411,7 @@ allocate_dynrelocs (struct elf_link_hash
 			s->size += htab->plt_entry_size;
 			/* After the 8192nd entry, room for two entries
 			   is allocated.  */
-			if (!htab->is_vxworks
+			if (htab->plt_type == PLT_OLD
 			    && (s->size - htab->plt_initial_entry_size)
 				/ htab->plt_entry_size
 			       > PLT_NUM_SINGLE_ENTRIES)
@@ -4418,7 +4425,7 @@ allocate_dynrelocs (struct elf_link_hash
 		  {
 		    htab->relplt->size += sizeof (Elf32_External_Rela);
 
-		    if (htab->is_vxworks)
+		    if (htab->plt_type == PLT_VXWORKS)
 		      {
 			/* Allocate space for the unloaded relocations.  */
 			if (!info->shared)
@@ -4659,9 +4666,9 @@ ppc_elf_size_dynamic_sections (bfd *outp
 	}
     }
 
-  if (htab->old_plt)
+  if (htab->plt_type == PLT_OLD)
     htab->got_header_size = 16;
-  else
+  else if (htab->plt_type == PLT_NEW)
     htab->got_header_size = 12;
 
   /* Set up .got offsets for local syms, and space for local dynamic
@@ -4775,7 +4782,7 @@ ppc_elf_size_dynamic_sections (bfd *outp
   /* Allocate space for global sym dynamic relocs.  */
   elf_link_hash_traverse (elf_hash_table (info), allocate_dynrelocs, info);
 
-  if (htab->got != NULL && !htab->is_vxworks)
+  if (htab->got != NULL && htab->plt_type != PLT_VXWORKS)
     {
       unsigned int g_o_t = 32768;
 
@@ -4786,7 +4793,7 @@ ppc_elf_size_dynamic_sections (bfd *outp
       if (htab->got->size <= 32768)
 	{
 	  g_o_t = htab->got->size;
-	  if (htab->old_plt)
+	  if (htab->plt_type == PLT_OLD)
 	    g_o_t += 4;
 	  htab->got->size += htab->got_header_size;
 	}
@@ -5122,7 +5129,7 @@ ppc_elf_relax_section (bfd *abfd,
 
 	      if (ent != NULL)
 		{
-		  if (!htab->old_plt)
+		  if (htab->plt_type == PLT_NEW)
 		    {
 		      tsec = htab->glink;
 		      toff = ent->glink_offset;
@@ -6337,7 +6344,7 @@ ppc_elf_relocate_section (bfd *output_bf
 	  {
 	    struct plt_entry *ent = find_plt_ent (h, got2, addend);
 
-	    if (!htab->old_plt)
+	    if (htab->plt_type == PLT_NEW)
 	      relocation = (htab->glink->output_section->vma
 			    + htab->glink->output_offset
 			    + ent->glink_offset);
@@ -6427,7 +6434,7 @@ ppc_elf_relocate_section (bfd *output_bf
 	      }
 
 	    unresolved_reloc = FALSE;
-	    if (!htab->old_plt)
+	    if (htab->plt_type == PLT_NEW)
 	      relocation = (htab->glink->output_section->vma
 			    + htab->glink->output_offset
 			    + ent->glink_offset);
@@ -6747,20 +6754,20 @@ ppc_elf_finish_dynamic_symbol (bfd *outp
 	    bfd_byte *loc;
 	    bfd_vma reloc_index;
 
-	    if (!(htab->old_plt || htab->is_vxworks))
+	    if (htab->plt_type == PLT_NEW)
 	      reloc_index = ent->plt.offset / 4;
 	    else
 	      {
 		reloc_index = ((ent->plt.offset - htab->plt_initial_entry_size)
 			       / htab->plt_slot_size);
 		if (reloc_index > PLT_NUM_SINGLE_ENTRIES
-		    && !htab->is_vxworks)
+		    && htab->plt_type == PLT_OLD)
 		  reloc_index -= (reloc_index - PLT_NUM_SINGLE_ENTRIES) / 2;
 	      }
 
 	    /* This symbol has an entry in the procedure linkage table.
 	       Set it up.  */
-	    if (htab->is_vxworks)
+	    if (htab->plt_type == PLT_VXWORKS)
 	      {
 		bfd_vma got_offset;
 		const bfd_vma *plt_entry;
@@ -6894,7 +6901,7 @@ ppc_elf_finish_dynamic_symbol (bfd *outp
 		rela.r_offset = (htab->plt->output_section->vma
 				 + htab->plt->output_offset
 				 + ent->plt.offset);
-		if (htab->old_plt)
+		if (htab->plt_type == PLT_OLD)
 		  {
 		    /* We don't need to fill in the .plt.  The ppc dynamic
 		       linker will fill it in.  */
@@ -6932,7 +6939,7 @@ ppc_elf_finish_dynamic_symbol (bfd *outp
 	    doneone = TRUE;
 	  }
 
-	if (!htab->old_plt)
+	if (htab->plt_type == PLT_NEW)
 	  {
 	    bfd_vma plt;
 	    unsigned char *p;
@@ -7154,7 +7161,7 @@ ppc_elf_finish_dynamic_sections (bfd *ou
       bfd_vma val;
 
       p += htab->elf.hgot->root.u.def.value;
-      if (htab->old_plt && !htab->is_vxworks)
+      if (htab->plt_type == PLT_OLD)
 	bfd_put_32 (output_bfd, 0x4e800021 /* blrl */, p - 4);
 
       val = 0;
@@ -7526,6 +7533,7 @@ ppc_elf_vxworks_link_hash_table_create (
       struct ppc_elf_link_hash_table *htab
         = (struct ppc_elf_link_hash_table *)ret;
       htab->is_vxworks = 1;
+      htab->plt_type = PLT_VXWORKS;
       htab->plt_entry_size = VXWORKS_PLT_ENTRY_SIZE;
       htab->plt_slot_size = VXWORKS_PLT_ENTRY_SIZE;
       htab->plt_initial_entry_size = VXWORKS_PLT_INITIAL_ENTRY_SIZE;
diff -uprN ../src.1/ld/emulparams/elf32ppccommon.sh ./ld/emulparams/elf32ppccommon.sh
--- ./ld/emulparams/elf32ppccommon.sh	1970-01-01 01:00:00.000000000 +0100
+++ ./ld/emulparams/elf32ppccommon.sh	2006-03-01 16:25:44.000000000 +0000
@@ -0,0 +1,49 @@
+# The PLT-agnostic parts of a generic 32-bit ELF PowerPC target.  Included by:
+# elf32ppc.sh elf32ppcvxworks.sh
+TEMPLATE_NAME=elf32
+GENERATE_SHLIB_SCRIPT=yes
+GENERATE_PIE_SCRIPT=yes
+SCRIPT_NAME=elf
+OUTPUT_FORMAT="elf32-powerpc"
+TEXT_START_ADDR=0x01800000
+MAXPAGESIZE=0x10000
+COMMONPAGESIZE=0x1000
+ARCH=powerpc:common
+MACHINE=
+EXECUTABLE_SYMBOLS='PROVIDE (__stack = 0); PROVIDE (___stack = 0);'
+if test -z "${CREATE_SHLIB}"; then
+  SDATA_START_SYMBOLS="PROVIDE (_SDA_BASE_ = 32768);"
+  SDATA2_START_SYMBOLS="PROVIDE (_SDA2_BASE_ = 32768);"
+  SBSS_START_SYMBOLS="PROVIDE (__sbss_start = .); PROVIDE (___sbss_start = .);"
+  SBSS_END_SYMBOLS="PROVIDE (__sbss_end = .); PROVIDE (___sbss_end = .);"
+else
+  unset SDATA_START_SYMBOLS
+  unset SDATA2_START_SYMBOLS
+  unset SBSS_START_SYMBOLS
+  unset SBSS_END_SYMBOLS
+fi
+OTHER_END_SYMBOLS="__end = .;"
+OTHER_RELRO_SECTIONS="
+  .fixup        ${RELOCATING-0} : { *(.fixup) }
+  .got1         ${RELOCATING-0} : { *(.got1) }
+  .got2         ${RELOCATING-0} : { *(.got2) }
+"
+OTHER_GOT_RELOC_SECTIONS="
+  .rela.got1         ${RELOCATING-0} : { *(.rela.got1) }
+  .rela.got2         ${RELOCATING-0} : { *(.rela.got2) }
+"
+
+# Treat a host that matches the target with the possible exception of "64"
+# in the name as if it were native.
+if test `echo "$host" | sed -e s/64//` = `echo "$target" | sed -e s/64//`; then
+  case " $EMULATION_LIBPATH " in
+    *" ${EMULATION_NAME} "*)
+      NATIVE=yes
+      ;;
+  esac
+fi
+
+# Look for 64 bit target libraries in /lib64, /usr/lib64 etc., first.
+case "$EMULATION_NAME" in
+  *64*) LIBPATH_SUFFIX=64 ;;
+esac
diff -uprN ../src.1/ld/emulparams/elf32ppc.sh ./ld/emulparams/elf32ppc.sh
--- ./ld/emulparams/elf32ppc.sh	2005-08-06 11:37:20.000000000 +0100
+++ ./ld/emulparams/elf32ppc.sh	2006-03-01 16:25:44.000000000 +0000
@@ -1,17 +1,7 @@
 # If you change this file, please also look at files which source this one:
-# elf32lppc.sh elf32ppclinux.sh elf32ppcsim.sh elf32ppcvxworks.sh
+# elf32lppc.sh elf32ppclinux.sh elf32ppcsim.sh
 
-TEMPLATE_NAME=elf32
-EXTRA_EM_FILE=ppc32elf
-GENERATE_SHLIB_SCRIPT=yes
-GENERATE_PIE_SCRIPT=yes
-SCRIPT_NAME=elf
-OUTPUT_FORMAT="elf32-powerpc"
-TEXT_START_ADDR=0x01800000
-MAXPAGESIZE=0x10000
-COMMONPAGESIZE=0x1000
-ARCH=powerpc:common
-MACHINE=
+. ${srcdir}/emulparams/elf32ppccommon.sh
 # Yes, we want duplicate .got and .plt sections.  The linker chooses the
 # appropriate one magically in ppc_after_open
 DATA_GOT=
@@ -22,40 +12,4 @@ GOT=".got          ${RELOCATING-0} : SPE
 PLT=".plt          ${RELOCATING-0} : SPECIAL { *(.plt) }"
 GOTPLT="${PLT}"
 OTHER_TEXT_SECTIONS="*(.glink)"
-EXECUTABLE_SYMBOLS='PROVIDE (__stack = 0); PROVIDE (___stack = 0);'
-if test -z "${CREATE_SHLIB}"; then
-  SDATA_START_SYMBOLS="PROVIDE (_SDA_BASE_ = 32768);"
-  SDATA2_START_SYMBOLS="PROVIDE (_SDA2_BASE_ = 32768);"
-  SBSS_START_SYMBOLS="PROVIDE (__sbss_start = .); PROVIDE (___sbss_start = .);"
-  SBSS_END_SYMBOLS="PROVIDE (__sbss_end = .); PROVIDE (___sbss_end = .);"
-else
-  unset SDATA_START_SYMBOLS
-  unset SDATA2_START_SYMBOLS
-  unset SBSS_START_SYMBOLS
-  unset SBSS_END_SYMBOLS
-fi
-OTHER_END_SYMBOLS="__end = .;"
-OTHER_RELRO_SECTIONS="
-  .fixup        ${RELOCATING-0} : { *(.fixup) }
-  .got1         ${RELOCATING-0} : { *(.got1) }
-  .got2         ${RELOCATING-0} : { *(.got2) }
-"
-OTHER_GOT_RELOC_SECTIONS="
-  .rela.got1         ${RELOCATING-0} : { *(.rela.got1) }
-  .rela.got2         ${RELOCATING-0} : { *(.rela.got2) }
-"
-
-# Treat a host that matches the target with the possible exception of "64"
-# in the name as if it were native.
-if test `echo "$host" | sed -e s/64//` = `echo "$target" | sed -e s/64//`; then
-  case " $EMULATION_LIBPATH " in
-    *" ${EMULATION_NAME} "*)
-      NATIVE=yes
-      ;;
-  esac
-fi
-
-# Look for 64 bit target libraries in /lib64, /usr/lib64 etc., first.
-case "$EMULATION_NAME" in
-  *64*) LIBPATH_SUFFIX=64 ;;
-esac
+EXTRA_EM_FILE=ppc32elf
diff -uprN ../src.1/ld/emulparams/elf32ppcvxworks.sh ./ld/emulparams/elf32ppcvxworks.sh
--- ./ld/emulparams/elf32ppcvxworks.sh	2006-03-01 14:17:55.000000000 +0000
+++ ./ld/emulparams/elf32ppcvxworks.sh	2006-03-01 16:25:44.000000000 +0000
@@ -1,4 +1,3 @@
-. ${srcdir}/emulparams/elf32ppc.sh
+. ${srcdir}/emulparams/elf32ppccommon.sh
 OUTPUT_FORMAT="elf32-powerpc-vxworks"
-unset BSS_PLT
 . ${srcdir}/emulparams/vxworks.sh
diff -uprN ../src.1/ld/Makefile.am ./ld/Makefile.am
--- ./ld/Makefile.am	2006-02-28 07:11:44.000000000 +0000
+++ ./ld/Makefile.am	2006-03-01 16:25:44.000000000 +0000
@@ -744,26 +744,30 @@ eelf32mipswindiss.c: $(srcdir)/emulparam
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32mipswindiss "$(tdir_elf32mipswindiss)"
 eelf32lppc.c: $(srcdir)/emulparams/elf32lppc.sh \
+  $(srcdir)/emulparams/elf32ppccommon.sh \
   $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32lppc "$(tdir_elf32lppc)"
 eelf32lppcnto.c: $(srcdir)/emulparams/elf32lppcnto.sh \
-  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
-  $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
+  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emulparams/elf32ppccommon.sh \
+  $(srcdir)/emultempl/ppc32elf.em $(srcdir)/emultempl/elf32.em \
+  $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32lppcnto "$(tdir_elf32lppcnto)"
 eelf32lppcsim.c: $(srcdir)/emulparams/elf32lppcsim.sh \
   $(srcdir)/emulparams/elf32lppc.sh $(srcdir)/emulparams/elf32ppc.sh \
-  $(srcdir)/emultempl/ppc32elf.em \
+  $(srcdir)/emulparams/elf32ppccommon.sh $(srcdir)/emultempl/ppc32elf.em \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32lppcsim "$(tdir_elf32lppcsim)"
 eelf32ppcnto.c: $(srcdir)/emulparams/elf32ppcnto.sh \
-  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
-  $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
+  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emulparams/elf32ppccommon.sh \
+  $(srcdir)/emultempl/ppc32elf.em $(srcdir)/emultempl/elf32.em \
+  $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppcnto "$(tdir_elf32ppcnto)"
 eelf32ppcwindiss.c: $(srcdir)/emulparams/elf32ppcwindiss.sh \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppcwindiss "$(tdir_elf32ppcwindiss)"
 eelf32ppcvxworks.c: $(srcdir)/emulparams/elf32ppcvxworks.sh \
+  $(srcdir)/emulparams/elf32ppccommon.sh $(srcdir)/emulparams/vxworks.sh \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppcvxworks "$(tdir_elf32ppcvxworks)"
 eelf32lsmip.c: $(srcdir)/emulparams/elf32lsmip.sh \
@@ -773,20 +777,24 @@ eelf32lsmip.c: $(srcdir)/emulparams/elf3
 eelf32openrisc.c: $(srcdir)/emulparams/elf32openrisc.sh \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32openrisc "$(tdir_openrisc)"
-eelf32ppc.c: $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
+eelf32ppc.c: $(srcdir)/emulparams/elf32ppc.sh \
+  $(srcdir)/emulparams/elf32ppccommon.sh $(srcdir)/emultempl/ppc32elf.em \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppc "$(tdir_elf32ppc)"
 eelf32ppc_fbsd.c: $(srcdir)/emulparams/elf32ppc_fbsd.sh \
-  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
-  $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
+  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emulparams/elf32ppccommon.sh \
+  $(srcdir)/emultempl/ppc32elf.em $(srcdir)/emultempl/elf32.em \
+  $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppc_fbsd "$(tdir_elf32ppc_fbsd)"
 eelf32ppcsim.c: $(srcdir)/emulparams/elf32ppcsim.sh \
-  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
-  $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
+  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emulparams/elf32ppccommon.sh \
+  $(srcdir)/emultempl/ppc32elf.em $(srcdir)/emultempl/elf32.em \
+  $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppcsim "$(tdir_elf32ppcsim)"
 eelf32ppclinux.c: $(srcdir)/emulparams/elf32ppclinux.sh \
-  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
-  $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
+  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emulparams/elf32ppccommon.sh \
+  $(srcdir)/emultempl/ppc32elf.em $(srcdir)/emultempl/elf32.em \
+  $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppclinux "$(tdir_elf32ppclinux)"
 eelf64ppc.c: $(srcdir)/emulparams/elf64ppc.sh $(srcdir)/emultempl/ppc64elf.em \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
diff -uprN ../src.1/ld/Makefile.in ./ld/Makefile.in
--- ./ld/Makefile.in	2006-02-28 07:11:44.000000000 +0000
+++ ./ld/Makefile.in	2006-03-01 16:25:44.000000000 +0000
@@ -1550,26 +1550,30 @@ eelf32mipswindiss.c: $(srcdir)/emulparam
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32mipswindiss "$(tdir_elf32mipswindiss)"
 eelf32lppc.c: $(srcdir)/emulparams/elf32lppc.sh \
+  $(srcdir)/emulparams/elf32ppccommon.sh \
   $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32lppc "$(tdir_elf32lppc)"
 eelf32lppcnto.c: $(srcdir)/emulparams/elf32lppcnto.sh \
-  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
-  $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
+  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emulparams/elf32ppccommon.sh \
+  $(srcdir)/emultempl/ppc32elf.em $(srcdir)/emultempl/elf32.em \
+  $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32lppcnto "$(tdir_elf32lppcnto)"
 eelf32lppcsim.c: $(srcdir)/emulparams/elf32lppcsim.sh \
   $(srcdir)/emulparams/elf32lppc.sh $(srcdir)/emulparams/elf32ppc.sh \
-  $(srcdir)/emultempl/ppc32elf.em \
+  $(srcdir)/emulparams/elf32ppccommon.sh $(srcdir)/emultempl/ppc32elf.em \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32lppcsim "$(tdir_elf32lppcsim)"
 eelf32ppcnto.c: $(srcdir)/emulparams/elf32ppcnto.sh \
-  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
-  $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
+  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emulparams/elf32ppccommon.sh \
+  $(srcdir)/emultempl/ppc32elf.em $(srcdir)/emultempl/elf32.em \
+  $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppcnto "$(tdir_elf32ppcnto)"
 eelf32ppcwindiss.c: $(srcdir)/emulparams/elf32ppcwindiss.sh \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppcwindiss "$(tdir_elf32ppcwindiss)"
 eelf32ppcvxworks.c: $(srcdir)/emulparams/elf32ppcvxworks.sh \
+  $(srcdir)/emulparams/elf32ppccommon.sh $(srcdir)/emulparams/vxworks.sh \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppcvxworks "$(tdir_elf32ppcvxworks)"
 eelf32lsmip.c: $(srcdir)/emulparams/elf32lsmip.sh \
@@ -1579,20 +1583,24 @@ eelf32lsmip.c: $(srcdir)/emulparams/elf3
 eelf32openrisc.c: $(srcdir)/emulparams/elf32openrisc.sh \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32openrisc "$(tdir_openrisc)"
-eelf32ppc.c: $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
+eelf32ppc.c: $(srcdir)/emulparams/elf32ppc.sh \
+  $(srcdir)/emulparams/elf32ppccommon.sh $(srcdir)/emultempl/ppc32elf.em \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppc "$(tdir_elf32ppc)"
 eelf32ppc_fbsd.c: $(srcdir)/emulparams/elf32ppc_fbsd.sh \
-  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
-  $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
+  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emulparams/elf32ppccommon.sh \
+  $(srcdir)/emultempl/ppc32elf.em $(srcdir)/emultempl/elf32.em \
+  $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppc_fbsd "$(tdir_elf32ppc_fbsd)"
 eelf32ppcsim.c: $(srcdir)/emulparams/elf32ppcsim.sh \
-  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
-  $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
+  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emulparams/elf32ppccommon.sh \
+  $(srcdir)/emultempl/ppc32elf.em $(srcdir)/emultempl/elf32.em \
+  $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppcsim "$(tdir_elf32ppcsim)"
 eelf32ppclinux.c: $(srcdir)/emulparams/elf32ppclinux.sh \
-  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emultempl/ppc32elf.em \
-  $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
+  $(srcdir)/emulparams/elf32ppc.sh $(srcdir)/emulparams/elf32ppccommon.sh \
+  $(srcdir)/emultempl/ppc32elf.em $(srcdir)/emultempl/elf32.em \
+  $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
 	${GENSCRIPTS} elf32ppclinux "$(tdir_elf32ppclinux)"
 eelf64ppc.c: $(srcdir)/emulparams/elf64ppc.sh $(srcdir)/emultempl/ppc64elf.em \
   $(srcdir)/emultempl/elf32.em $(srcdir)/scripttempl/elf.sc ${GEN_DEPENDS}
diff -uprN ../src.1/ld/testsuite/ld-powerpc/powerpc.exp ./ld/testsuite/ld-powerpc/powerpc.exp
--- ./ld/testsuite/ld-powerpc/powerpc.exp	2005-10-14 16:09:22.000000000 +0100
+++ ./ld/testsuite/ld-powerpc/powerpc.exp	2006-03-01 15:50:19.000000000 +0000
@@ -20,6 +20,25 @@ if { ![istarget "powerpc*-*-*"]	} {
     return
 }
 
+if {[istarget "*-*-vxworks"]} {
+    set ppcvxtests {
+	{"VxWorks shared library test 1 (default script)" "-shared"
+	 "-mregnames" {vxworks1-lib.s}
+	 {{readelf --segments vxworks1-lib.sd}}
+	 "libvxworks1.so"}
+	{"VxWorks shared library test 1" "-shared -Tvxworks1.ld"
+	 "-mregnames" {vxworks1-lib.s}
+	 {{readelf --relocs vxworks1-lib.rd} {objdump -dr vxworks1-lib.dd}}
+	 "libvxworks1.so"}
+	{"VxWorks dynamic executable test 1" \
+	 "tmpdir/libvxworks1.so -Tvxworks1.ld -q" "-mregnames" {vxworks1.s}
+	 {{readelf --relocs vxworks1.rd} {objdump -dr vxworks1.dd}}
+	 "vxworks1"}
+    }
+    run_ld_link_tests $ppcvxtests
+    return
+}
+
 # powerpc ELF only at the moment.
 
 if { [istarget "*-*-macos*"] || [istarget "*-*-netware*"]
diff -uprN ../src.1/ld/testsuite/ld-powerpc/vxworks1.dd ./ld/testsuite/ld-powerpc/vxworks1.dd
--- ./ld/testsuite/ld-powerpc/vxworks1.dd	1970-01-01 01:00:00.000000000 +0100
+++ ./ld/testsuite/ld-powerpc/vxworks1.dd	2006-03-01 14:07:10.000000000 +0000
@@ -0,0 +1,48 @@
+
+.*:     file format .*
+
+Disassembly of section \.plt:
+
+00080800 <_PROCEDURE_LINKAGE_TABLE_>:
+   80800:	3d 80 00 08 	lis     r12,8
+			80802: R_PPC_ADDR16_HA	_GLOBAL_OFFSET_TABLE_
+   80804:	39 8c 14 00 	addi    r12,r12,5120
+			80806: R_PPC_ADDR16_LO	_GLOBAL_OFFSET_TABLE_
+   80808:	80 0c 00 08 	lwz     r0,8\(r12\)
+   8080c:	7c 09 03 a6 	mtctr   r0
+   80810:	81 8c 00 04 	lwz     r12,4\(r12\)
+   80814:	4e 80 04 20 	bctr
+   80818:	60 00 00 00 	nop
+   8081c:	60 00 00 00 	nop
+   80820:	3d 80 00 08 	lis     r12,8
+			80822: R_PPC_ADDR16_HA	_GLOBAL_OFFSET_TABLE_\+0xc
+   80824:	81 8c 14 0c 	lwz     r12,5132\(r12\)
+			80826: R_PPC_ADDR16_LO	_GLOBAL_OFFSET_TABLE_\+0xc
+   80828:	7d 89 03 a6 	mtctr   r12
+   8082c:	4e 80 04 20 	bctr
+   80830:	39 60 00 00 	li      r11,0
+   80834:	4b ff ff cc 	b       80800 <_PROCEDURE_LINKAGE_TABLE_>
+   80838:	60 00 00 00 	nop
+   8083c:	60 00 00 00 	nop
+   80840:	3d 80 00 08 	lis     r12,8
+			80842: R_PPC_ADDR16_HA	_GLOBAL_OFFSET_TABLE_\+0x10
+   80844:	81 8c 14 10 	lwz     r12,5136\(r12\)
+			80846: R_PPC_ADDR16_LO	_GLOBAL_OFFSET_TABLE_\+0x10
+   80848:	7d 89 03 a6 	mtctr   r12
+   8084c:	4e 80 04 20 	bctr
+   80850:	39 60 00 01 	li      r11,1
+   80854:	4b ff ff ac 	b       80800 <_PROCEDURE_LINKAGE_TABLE_>
+   80858:	60 00 00 00 	nop
+   8085c:	60 00 00 00 	nop
+Disassembly of section \.text:
+
+00080c00 <_start>:
+   80c00:	4b ff fc 41 	bl      80840 <_PROCEDURE_LINKAGE_TABLE_\+0x40>
+			80c00: R_PPC_PLTREL24	\.plt\+0x40
+   80c04:	48 00 00 09 	bl      80c0c <sexternal>
+			80c04: R_PPC_PLTREL24	sexternal
+   80c08:	4b ff fc 19 	bl      80820 <_PROCEDURE_LINKAGE_TABLE_\+0x20>
+			80c08: R_PPC_PLTREL24	\.plt\+0x20
+
+00080c0c <sexternal>:
+   80c0c:	4e 80 00 20 	blr
diff -uprN ../src.1/ld/testsuite/ld-powerpc/vxworks1.ld ./ld/testsuite/ld-powerpc/vxworks1.ld
--- ./ld/testsuite/ld-powerpc/vxworks1.ld	1970-01-01 01:00:00.000000000 +0100
+++ ./ld/testsuite/ld-powerpc/vxworks1.ld	2006-03-01 13:59:39.000000000 +0000
@@ -0,0 +1,27 @@
+SECTIONS
+{
+  . = 0x80000;
+  .interp : { *(.interp) }
+  .hash : { *(.hash) }
+  .dynsym : { *(.dynsym) }
+  .dynstr : { *(.dynstr) }
+
+  . = ALIGN (0x400);
+  .rela.dyn : { *(.rela.dyn) }
+  .rela.plt : { *(.rela.plt) }
+
+  . = ALIGN (0x400);
+  .plt : { *(.plt) }
+
+  . = ALIGN (0x400);
+  .text : { *(.text) }
+
+  . = ALIGN (0x1000);
+  .dynamic : { *(.dynamic) }
+
+  . = ALIGN (0x400);
+  .got : { *(.got.plt) *(.got) }
+
+  . = ALIGN (0x400);
+  .bss : { *(.bss) }
+}
diff -uprN ../src.1/ld/testsuite/ld-powerpc/vxworks1-lib.dd ./ld/testsuite/ld-powerpc/vxworks1-lib.dd
--- ./ld/testsuite/ld-powerpc/vxworks1-lib.dd	1970-01-01 01:00:00.000000000 +0100
+++ ./ld/testsuite/ld-powerpc/vxworks1-lib.dd	2006-03-01 14:03:34.000000000 +0000
@@ -0,0 +1,56 @@
+
+.*:     file format .*
+
+Disassembly of section \.plt:
+
+00080800 <_PROCEDURE_LINKAGE_TABLE_>:
+   80800:	81 9e 00 08 	lwz     r12,8\(r30\)
+   80804:	7d 89 03 a6 	mtctr   r12
+   80808:	81 9e 00 04 	lwz     r12,4\(r30\)
+   8080c:	4e 80 04 20 	bctr
+   80810:	60 00 00 00 	nop
+   80814:	60 00 00 00 	nop
+   80818:	60 00 00 00 	nop
+   8081c:	60 00 00 00 	nop
+   80820:	3d 9e 00 00 	addis   r12,r30,0
+   80824:	81 8c 00 0c 	lwz     r12,12\(r12\)
+   80828:	7d 89 03 a6 	mtctr   r12
+   8082c:	4e 80 04 20 	bctr
+   80830:	39 60 00 00 	li      r11,0
+   80834:	4b ff ff cc 	b       80800 <_PROCEDURE_LINKAGE_TABLE_>
+   80838:	60 00 00 00 	nop
+   8083c:	60 00 00 00 	nop
+   80840:	3d 9e 00 00 	addis   r12,r30,0
+   80844:	81 8c 00 10 	lwz     r12,16\(r12\)
+   80848:	7d 89 03 a6 	mtctr   r12
+   8084c:	4e 80 04 20 	bctr
+   80850:	39 60 00 01 	li      r11,1
+   80854:	4b ff ff ac 	b       80800 <_PROCEDURE_LINKAGE_TABLE_>
+   80858:	60 00 00 00 	nop
+   8085c:	60 00 00 00 	nop
+Disassembly of section \.text:
+
+00080c00 <foo>:
+   80c00:	94 21 ff e8 	stwu    r1,-24\(r1\)
+   80c04:	7c 08 02 a6 	mflr    r0
+   80c08:	90 01 00 1c 	stw     r0,28\(r1\)
+   80c0c:	3f c0 00 00 	lis     r30,0
+   80c10:	83 de 00 00 	lwz     r30,0\(r30\)
+   80c14:	83 de 00 00 	lwz     r30,0\(r30\)
+   80c18:	80 3e 00 14 	lwz     r1,20\(r30\)
+   80c1c:	80 01 00 00 	lwz     r0,0\(r1\)
+   80c20:	38 00 00 01 	li      r0,1
+   80c24:	90 01 00 00 	stw     r0,0\(r1\)
+   80c28:	48 00 00 1d 	bl      80c44 <slocal>
+   80c2c:	4b ff fc 15 	bl      80840 <_PROCEDURE_LINKAGE_TABLE_\+0x40>
+   80c30:	4b ff fb f1 	bl      80820 <_PROCEDURE_LINKAGE_TABLE_\+0x20>
+   80c34:	80 01 00 1c 	lwz     r0,28\(r1\)
+   80c38:	7c 08 03 a6 	mtlr    r0
+   80c3c:	38 21 00 18 	addi    r1,r1,24
+   80c40:	4e 80 00 20 	blr
+
+00080c44 <slocal>:
+   80c44:	4e 80 00 20 	blr
+
+00080c48 <sglobal>:
+   80c48:	4e 80 00 20 	blr
diff -uprN ../src.1/ld/testsuite/ld-powerpc/vxworks1-lib.rd ./ld/testsuite/ld-powerpc/vxworks1-lib.rd
--- ./ld/testsuite/ld-powerpc/vxworks1-lib.rd	1970-01-01 01:00:00.000000000 +0100
+++ ./ld/testsuite/ld-powerpc/vxworks1-lib.rd	2006-03-01 14:01:58.000000000 +0000
@@ -0,0 +1,12 @@
+
+Relocation section '\.rela\.plt' at offset .* contains 2 entries:
+ Offset     Info    Type            Sym\.Value  Sym\. Name \+ Addend
+0008140c  .*15 R_PPC_JMP_SLOT    00000000   sexternal \+ 0
+00081410  .*15 R_PPC_JMP_SLOT    00080c48   sglobal \+ 0
+
+Relocation section '\.rela\.dyn' at offset .* contains 4 entries:
+ Offset     Info    Type            Sym\.Value  Sym\. Name \+ Addend
+00080c0e  .*06 R_PPC_ADDR16_HA   00000000   __GOTT_BASE__ \+ 0
+00080c12  .*04 R_PPC_ADDR16_LO   00000000   __GOTT_BASE__ \+ 0
+00080c16  .*03 R_PPC_ADDR16      00000000   __GOTT_INDEX__ \+ 0
+00081414  .*14 R_PPC_GLOB_DAT    00081800   x \+ 0
diff -uprN ../src.1/ld/testsuite/ld-powerpc/vxworks1-lib.s ./ld/testsuite/ld-powerpc/vxworks1-lib.s
--- ./ld/testsuite/ld-powerpc/vxworks1-lib.s	1970-01-01 01:00:00.000000000 +0100
+++ ./ld/testsuite/ld-powerpc/vxworks1-lib.s	2006-03-01 15:59:03.000000000 +0000
@@ -0,0 +1,35 @@
+	.text
+	.globl	foo
+	.type	foo, @function
+foo:
+	stwu	r1,-24(r1)
+	mflr	r0
+	stw	r0,28(r1)
+	lis	r30,__GOTT_BASE__@ha
+	lwz	r30,__GOTT_BASE__@l(r30)
+	lwz	r30,__GOTT_INDEX__(r30)
+	lwz	r1,x@got(r30)
+	lwz	r0,0(r1)
+	addi	r0,r0,1
+	stw	r0,0(r1)
+	bl	slocal
+	bl	sglobal@plt
+	bl	sexternal@plt
+	lwz	r0,28(r1)
+	mtlr	r0
+	addi	r1,r1,24
+	blr
+	.size	foo, .-foo
+
+	.type	slocal, @function
+slocal:
+	blr
+	.size	slocal, .-slocal
+
+	.globl	sglobal
+	.type	sglobal, @function
+sglobal:
+	blr
+	.size	sglobal, .-sglobal
+
+	.comm	x,4,4
diff -uprN ../src.1/ld/testsuite/ld-powerpc/vxworks1-lib.sd ./ld/testsuite/ld-powerpc/vxworks1-lib.sd
--- ./ld/testsuite/ld-powerpc/vxworks1-lib.sd	1970-01-01 01:00:00.000000000 +0100
+++ ./ld/testsuite/ld-powerpc/vxworks1-lib.sd	2006-03-01 16:26:38.000000000 +0000
@@ -0,0 +1,12 @@
+#...
+Program Headers:
+  Type .* Flg Align
+  LOAD .* R E 0x10000
+  LOAD .* RW  0x10000
+  DYNAMIC .* RW  0x4
+
+ Section to Segment mapping:
+  Segment Sections\.\.\.
+   00 .* \.plt .*
+   01 .* \.got .*
+   02 .* \.dynamic $
diff -uprN ../src.1/ld/testsuite/ld-powerpc/vxworks1.rd ./ld/testsuite/ld-powerpc/vxworks1.rd
--- ./ld/testsuite/ld-powerpc/vxworks1.rd	1970-01-01 01:00:00.000000000 +0100
+++ ./ld/testsuite/ld-powerpc/vxworks1.rd	2006-03-01 14:05:33.000000000 +0000
@@ -0,0 +1,22 @@
+
+Relocation section '\.rela\.plt' at offset .* contains 2 entries:
+ Offset     Info    Type            Sym\.Value  Sym\. Name \+ Addend
+0008140c  .*15 R_PPC_JMP_SLOT    00080820   sglobal \+ 0
+00081410  .*15 R_PPC_JMP_SLOT    00080840   foo \+ 0
+
+Relocation section '\.rela\.text' at offset .* contains 3 entries:
+ Offset     Info    Type            Sym\.Value  Sym\. Name \+ Addend
+00080c00  .*12 R_PPC_PLTREL24    00080800   \.plt \+ 40
+00080c04  .*12 R_PPC_PLTREL24    00080c0c   sexternal \+ 0
+00080c08  .*12 R_PPC_PLTREL24    00080800   \.plt \+ 20
+
+Relocation section '\.rela\.plt\.unloaded' at offset .* contains 8 entries:
+ Offset     Info    Type            Sym\.Value  Sym\. Name \+ Addend
+00080802  .*06 R_PPC_ADDR16_HA   00081400   _GLOBAL_OFFSET_TABLE_ \+ 0
+00080806  .*04 R_PPC_ADDR16_LO   00081400   _GLOBAL_OFFSET_TABLE_ \+ 0
+00080822  .*06 R_PPC_ADDR16_HA   00081400   _GLOBAL_OFFSET_TABLE_ \+ c
+00080826  .*04 R_PPC_ADDR16_LO   00081400   _GLOBAL_OFFSET_TABLE_ \+ c
+0008140c  .*01 R_PPC_ADDR32      00080800   _PROCEDURE_LINKAGE_TAB.* \+ 30
+00080842  .*06 R_PPC_ADDR16_HA   00081400   _GLOBAL_OFFSET_TABLE_ \+ 10
+00080846  .*04 R_PPC_ADDR16_LO   00081400   _GLOBAL_OFFSET_TABLE_ \+ 10
+00081410  .*01 R_PPC_ADDR32      00080800   _PROCEDURE_LINKAGE_TAB.* \+ 50
diff -uprN ../src.1/ld/testsuite/ld-powerpc/vxworks1.s ./ld/testsuite/ld-powerpc/vxworks1.s
--- ./ld/testsuite/ld-powerpc/vxworks1.s	1970-01-01 01:00:00.000000000 +0100
+++ ./ld/testsuite/ld-powerpc/vxworks1.s	2006-03-01 13:51:07.000000000 +0000
@@ -0,0 +1,14 @@
+	.text
+	.globl	_start
+	.type	_start,@function
+_start:
+	bl	foo@plt
+	bl	sexternal@plt
+	bl	sglobal@plt
+	.size	_start, .-_start
+
+	.globl	sexternal
+	.type	sexternal,@function
+sexternal:
+	blr
+	.size	sexternal, .-sexternal



More information about the Binutils mailing list