/* Renesas / SuperH SH specific support for 32-bit ELF
   Copyright (C) 1996-2017 Free Software Foundation, Inc.
   Contributed by Ian Lance Taylor, Cygnus Support.

   This file is part of BFD, the Binary File Descriptor library.

   This program is free software; you can redistribute it and/or modify
   it under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 3 of the License, or
   (at your option) any later version.

   This program is distributed in the hope that it will be useful,
   but WITHOUT ANY WARRANTY; without even the implied warranty of
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   GNU General Public License for more details.

   You should have received a copy of the GNU General Public License
   along with this program; if not, write to the Free Software
   Foundation, Inc., 51 Franklin Street - Fifth Floor, Boston,
   MA 02110-1301, USA.  */

#include "sysdep.h"
#include "bfd.h"
#include "bfdlink.h"
#include "libbfd.h"
#include "elf-bfd.h"
#include "elf-vxworks.h"
#include "elf/sh.h"
#include "dwarf2.h"
#include "libiberty.h"
#include "../opcodes/sh-opc.h"

static bfd_reloc_status_type sh_elf_reloc
  (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
static bfd_reloc_status_type sh_elf_ignore_reloc
  (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
static bfd_boolean sh_elf_relax_delete_bytes
  (bfd *, asection *, bfd_vma, int);
static bfd_boolean sh_elf_align_loads
  (bfd *, asection *, Elf_Internal_Rela *, bfd_byte *, bfd_boolean *);
#ifndef SH64_ELF
static bfd_boolean sh_elf_swap_insns
  (bfd *, asection *, void *, bfd_byte *, bfd_vma);
#endif
static int sh_elf_optimized_tls_reloc
  (struct bfd_link_info *, int, int);
static bfd_vma dtpoff_base
  (struct bfd_link_info *);
static bfd_vma tpoff
  (struct bfd_link_info *, bfd_vma);

/* The name of the dynamic interpreter.  This is put in the .interp
   section.  */

#define ELF_DYNAMIC_INTERPRETER "/usr/lib/libc.so.1"

/* FDPIC binaries have a default 128K stack.  */
#define DEFAULT_STACK_SIZE 0x20000

#define MINUS_ONE ((bfd_vma) 0 - 1)

/* Decide whether a reference to a symbol can be resolved locally or
   not.  If the symbol is protected, we want the local address, but
   its function descriptor must be assigned by the dynamic linker.  */
#define SYMBOL_FUNCDESC_LOCAL(INFO, H) \
  (SYMBOL_REFERENCES_LOCAL (INFO, H) \
   || ! elf_hash_table (INFO)->dynamic_sections_created)

#define SH_PARTIAL32 TRUE
#define SH_SRC_MASK32 0xffffffff
#define SH_ELF_RELOC sh_elf_reloc
static reloc_howto_type sh_elf_howto_table[] =
{
#include "elf32-sh-relocs.h"
};

#define SH_PARTIAL32 FALSE
#define SH_SRC_MASK32 0
#define SH_ELF_RELOC bfd_elf_generic_reloc
static reloc_howto_type sh_vxworks_howto_table[] =
{
#include "elf32-sh-relocs.h"
};

/* Return true if OUTPUT_BFD is a VxWorks object.  */

static bfd_boolean
vxworks_object_p (bfd *abfd ATTRIBUTE_UNUSED)
{
#if !defined INCLUDE_SHMEDIA && !defined SH_TARGET_ALREADY_DEFINED
  extern const bfd_target sh_elf32_vxworks_le_vec;
  extern const bfd_target sh_elf32_vxworks_vec;

  return (abfd->xvec == &sh_elf32_vxworks_le_vec
	  || abfd->xvec == &sh_elf32_vxworks_vec);
#else
  return FALSE;
#endif
}

/* Return true if OUTPUT_BFD is an FDPIC object.  */

static bfd_boolean
fdpic_object_p (bfd *abfd ATTRIBUTE_UNUSED)
{
#if !defined INCLUDE_SHMEDIA && !defined SH_TARGET_ALREADY_DEFINED
  extern const bfd_target sh_elf32_fdpic_le_vec;
  extern const bfd_target sh_elf32_fdpic_be_vec;

  return (abfd->xvec == &sh_elf32_fdpic_le_vec
	  || abfd->xvec == &sh_elf32_fdpic_be_vec);
#else
  return FALSE;
#endif
}

/* Return the howto table for ABFD.  */

static reloc_howto_type *
get_howto_table (bfd *abfd)
{
  if (vxworks_object_p (abfd))
    return sh_vxworks_howto_table;
  return sh_elf_howto_table;
}

static bfd_reloc_status_type
sh_elf_reloc_loop (int r_type ATTRIBUTE_UNUSED, bfd *input_bfd,
		   asection *input_section, bfd_byte *contents,
		   bfd_vma addr, asection *symbol_section,
		   bfd_vma start, bfd_vma end)
{
  static bfd_vma last_addr;
  static asection *last_symbol_section;
  bfd_byte *start_ptr, *ptr, *last_ptr;
  int diff, cum_diff;
  bfd_signed_vma x;
  int insn;

  /* Sanity check the address.  */
  if (addr > bfd_get_section_limit (input_bfd, input_section))
    return bfd_reloc_outofrange;

  /* We require the start and end relocations to be processed consecutively -
     although we allow then to be processed forwards or backwards.  */
  if (! last_addr)
    {
      last_addr = addr;
      last_symbol_section = symbol_section;
      return bfd_reloc_ok;
    }
  if (last_addr != addr)
    abort ();
  last_addr = 0;

  if (! symbol_section || last_symbol_section != symbol_section || end < start)
    return bfd_reloc_outofrange;

  /* Get the symbol_section contents.  */
  if (symbol_section != input_section)
    {
      if (elf_section_data (symbol_section)->this_hdr.contents != NULL)
	contents = elf_section_data (symbol_section)->this_hdr.contents;
      else
	{
	  if (!bfd_malloc_and_get_section (input_bfd, symbol_section,
					   &contents))
	    {
	      if (contents != NULL)
		free (contents);
	      return bfd_reloc_outofrange;
	    }
	}
    }
#define IS_PPI(PTR) ((bfd_get_16 (input_bfd, (PTR)) & 0xfc00) == 0xf800)
  start_ptr = contents + start;
  for (cum_diff = -6, ptr = contents + end; cum_diff < 0 && ptr > start_ptr;)
    {
      for (last_ptr = ptr, ptr -= 4; ptr >= start_ptr && IS_PPI (ptr);)
	ptr -= 2;
      ptr += 2;
      diff = (last_ptr - ptr) >> 1;
      cum_diff += diff & 1;
      cum_diff += diff;
    }
  /* Calculate the start / end values to load into rs / re minus four -
     so that will cancel out the four we would otherwise have to add to
     addr to get the value to subtract in order to get relative addressing.  */
  if (cum_diff >= 0)
    {
      start -= 4;
      end = (ptr + cum_diff * 2) - contents;
    }
  else
    {
      bfd_vma start0 = start - 4;

      while (start0 && IS_PPI (contents + start0))
	start0 -= 2;
      start0 = start - 2 - ((start - start0) & 2);
      start = start0 - cum_diff - 2;
      end = start0;
    }

  if (contents != NULL
      && elf_section_data (symbol_section)->this_hdr.contents != contents)
    free (contents);

  insn = bfd_get_16 (input_bfd, contents + addr);

  x = (insn & 0x200 ? end : start) - addr;
  if (input_section != symbol_section)
    x += ((symbol_section->output_section->vma + symbol_section->output_offset)
	  - (input_section->output_section->vma
	     + input_section->output_offset));
  x >>= 1;
  if (x < -128 || x > 127)
    return bfd_reloc_overflow;

  x = (insn & ~0xff) | (x & 0xff);
  bfd_put_16 (input_bfd, (bfd_vma) x, contents + addr);

  return bfd_reloc_ok;
}

/* This function is used for normal relocs.  This used to be like the COFF
   function, and is almost certainly incorrect for other ELF targets.  */

static bfd_reloc_status_type
sh_elf_reloc (bfd *abfd, arelent *reloc_entry, asymbol *symbol_in,
	      void *data, asection *input_section, bfd *output_bfd,
	      char **error_message ATTRIBUTE_UNUSED)
{
  unsigned long insn;
  bfd_vma sym_value;
  enum elf_sh_reloc_type r_type;
  bfd_vma addr = reloc_entry->address;
  bfd_byte *hit_data = addr + (bfd_byte *) data;

  r_type = (enum elf_sh_reloc_type) reloc_entry->howto->type;

  if (output_bfd != NULL)
    {
      /* Partial linking--do nothing.  */
      reloc_entry->address += input_section->output_offset;
      return bfd_reloc_ok;
    }

  /* Almost all relocs have to do with relaxing.  If any work must be
     done for them, it has been done in sh_relax_section.  */
  if (r_type == R_SH_IND12W && (symbol_in->flags & BSF_LOCAL) != 0)
    return bfd_reloc_ok;

  if (symbol_in != NULL
      && bfd_is_und_section (symbol_in->section))
    return bfd_reloc_undefined;

  /* PR 17512: file: 9891ca98.  */
  if (addr * bfd_octets_per_byte (abfd) + bfd_get_reloc_size (reloc_entry->howto)
      > bfd_get_section_limit_octets (abfd, input_section))
    return bfd_reloc_outofrange;

  if (bfd_is_com_section (symbol_in->section))
    sym_value = 0;
  else
    sym_value = (symbol_in->value +
		 symbol_in->section->output_section->vma +
		 symbol_in->section->output_offset);

  switch (r_type)
    {
    case R_SH_DIR32:
      insn = bfd_get_32 (abfd, hit_data);
      insn += sym_value + reloc_entry->addend;
      bfd_put_32 (abfd, (bfd_vma) insn, hit_data);
      break;
    case R_SH_IND12W:
      insn = bfd_get_16 (abfd, hit_data);
      sym_value += reloc_entry->addend;
      sym_value -= (input_section->output_section->vma
		    + input_section->output_offset
		    + addr
		    + 4);
      sym_value += (insn & 0xfff) << 1;
      if (insn & 0x800)
	sym_value -= 0x1000;
      insn = (insn & 0xf000) | (sym_value & 0xfff);
      bfd_put_16 (abfd, (bfd_vma) insn, hit_data);
      if (sym_value < (bfd_vma) -0x1000 || sym_value >= 0x1000)
	return bfd_reloc_overflow;
      break;
    default:
      abort ();
      break;
    }

  return bfd_reloc_ok;
}

/* This function is used for relocs which are only used for relaxing,
   which the linker should otherwise ignore.  */

static bfd_reloc_status_type
sh_elf_ignore_reloc (bfd *abfd ATTRIBUTE_UNUSED, arelent *reloc_entry,
		     asymbol *symbol ATTRIBUTE_UNUSED,
		     void *data ATTRIBUTE_UNUSED, asection *input_section,
		     bfd *output_bfd,
		     char **error_message ATTRIBUTE_UNUSED)
{
  if (output_bfd != NULL)
    reloc_entry->address += input_section->output_offset;
  return bfd_reloc_ok;
}

/* This structure is used to map BFD reloc codes to SH ELF relocs.  */

struct elf_reloc_map
{
  bfd_reloc_code_real_type bfd_reloc_val;
  unsigned char elf_reloc_val;
};

/* An array mapping BFD reloc codes to SH ELF relocs.  */

static const struct elf_reloc_map sh_reloc_map[] =
{
  { BFD_RELOC_NONE, R_SH_NONE },
  { BFD_RELOC_32, R_SH_DIR32 },
  { BFD_RELOC_16, R_SH_DIR16 },
  { BFD_RELOC_8, R_SH_DIR8 },
  { BFD_RELOC_CTOR, R_SH_DIR32 },
  { BFD_RELOC_32_PCREL, R_SH_REL32 },
  { BFD_RELOC_SH_PCDISP8BY2, R_SH_DIR8WPN },
  { BFD_RELOC_SH_PCDISP12BY2, R_SH_IND12W },
  { BFD_RELOC_SH_PCRELIMM8BY2, R_SH_DIR8WPZ },
  { BFD_RELOC_SH_PCRELIMM8BY4, R_SH_DIR8WPL },
  { BFD_RELOC_8_PCREL, R_SH_SWITCH8 },
  { BFD_RELOC_SH_SWITCH16, R_SH_SWITCH16 },
  { BFD_RELOC_SH_SWITCH32, R_SH_SWITCH32 },
  { BFD_RELOC_SH_USES, R_SH_USES },
  { BFD_RELOC_SH_COUNT, R_SH_COUNT },
  { BFD_RELOC_SH_ALIGN, R_SH_ALIGN },
  { BFD_RELOC_SH_CODE, R_SH_CODE },
  { BFD_RELOC_SH_DATA, R_SH_DATA },
  { BFD_RELOC_SH_LABEL, R_SH_LABEL },
  { BFD_RELOC_VTABLE_INHERIT, R_SH_GNU_VTINHERIT },
  { BFD_RELOC_VTABLE_ENTRY, R_SH_GNU_VTENTRY },
  { BFD_RELOC_SH_LOOP_START, R_SH_LOOP_START },
  { BFD_RELOC_SH_LOOP_END, R_SH_LOOP_END },
  { BFD_RELOC_SH_TLS_GD_32, R_SH_TLS_GD_32 },
  { BFD_RELOC_SH_TLS_LD_32, R_SH_TLS_LD_32 },
  { BFD_RELOC_SH_TLS_LDO_32, R_SH_TLS_LDO_32 },
  { BFD_RELOC_SH_TLS_IE_32, R_SH_TLS_IE_32 },
  { BFD_RELOC_SH_TLS_LE_32, R_SH_TLS_LE_32 },
  { BFD_RELOC_SH_TLS_DTPMOD32, R_SH_TLS_DTPMOD32 },
  { BFD_RELOC_SH_TLS_DTPOFF32, R_SH_TLS_DTPOFF32 },
  { BFD_RELOC_SH_TLS_TPOFF32, R_SH_TLS_TPOFF32 },
  { BFD_RELOC_32_GOT_PCREL, R_SH_GOT32 },
  { BFD_RELOC_32_PLT_PCREL, R_SH_PLT32 },
  { BFD_RELOC_SH_COPY, R_SH_COPY },
  { BFD_RELOC_SH_GLOB_DAT, R_SH_GLOB_DAT },
  { BFD_RELOC_SH_JMP_SLOT, R_SH_JMP_SLOT },
  { BFD_RELOC_SH_RELATIVE, R_SH_RELATIVE },
  { BFD_RELOC_32_GOTOFF, R_SH_GOTOFF },
  { BFD_RELOC_SH_GOTPC, R_SH_GOTPC },
  { BFD_RELOC_SH_GOTPLT32, R_SH_GOTPLT32 },
  { BFD_RELOC_SH_GOT20, R_SH_GOT20 },
  { BFD_RELOC_SH_GOTOFF20, R_SH_GOTOFF20 },
  { BFD_RELOC_SH_GOTFUNCDESC, R_SH_GOTFUNCDESC },
  { BFD_RELOC_SH_GOTFUNCDESC20, R_SH_GOTFUNCDESC20 },
  { BFD_RELOC_SH_GOTOFFFUNCDESC, R_SH_GOTOFFFUNCDESC },
  { BFD_RELOC_SH_GOTOFFFUNCDESC20, R_SH_GOTOFFFUNCDESC20 },
  { BFD_RELOC_SH_FUNCDESC, R_SH_FUNCDESC },
#ifdef INCLUDE_SHMEDIA
  { BFD_RELOC_SH_GOT_LOW16, R_SH_GOT_LOW16 },
  { BFD_RELOC_SH_GOT_MEDLOW16, R_SH_GOT_MEDLOW16 },
  { BFD_RELOC_SH_GOT_MEDHI16, R_SH_GOT_MEDHI16 },
  { BFD_RELOC_SH_GOT_HI16, R_SH_GOT_HI16 },
  { BFD_RELOC_SH_GOTPLT_LOW16, R_SH_GOTPLT_LOW16 },
  { BFD_RELOC_SH_GOTPLT_MEDLOW16, R_SH_GOTPLT_MEDLOW16 },
  { BFD_RELOC_SH_GOTPLT_MEDHI16, R_SH_GOTPLT_MEDHI16 },
  { BFD_RELOC_SH_GOTPLT_HI16, R_SH_GOTPLT_HI16 },
  { BFD_RELOC_SH_PLT_LOW16, R_SH_PLT_LOW16 },
  { BFD_RELOC_SH_PLT_MEDLOW16, R_SH_PLT_MEDLOW16 },
  { BFD_RELOC_SH_PLT_MEDHI16, R_SH_PLT_MEDHI16 },
  { BFD_RELOC_SH_PLT_HI16, R_SH_PLT_HI16 },
  { BFD_RELOC_SH_GOTOFF_LOW16, R_SH_GOTOFF_LOW16 },
  { BFD_RELOC_SH_GOTOFF_MEDLOW16, R_SH_GOTOFF_MEDLOW16 },
  { BFD_RELOC_SH_GOTOFF_MEDHI16, R_SH_GOTOFF_MEDHI16 },
  { BFD_RELOC_SH_GOTOFF_HI16, R_SH_GOTOFF_HI16 },
  { BFD_RELOC_SH_GOTPC_LOW16, R_SH_GOTPC_LOW16 },
  { BFD_RELOC_SH_GOTPC_MEDLOW16, R_SH_GOTPC_MEDLOW16 },
  { BFD_RELOC_SH_GOTPC_MEDHI16, R_SH_GOTPC_MEDHI16 },
  { BFD_RELOC_SH_GOTPC_HI16, R_SH_GOTPC_HI16 },
  { BFD_RELOC_SH_COPY64, R_SH_COPY64 },
  { BFD_RELOC_SH_GLOB_DAT64, R_SH_GLOB_DAT64 },
  { BFD_RELOC_SH_JMP_SLOT64, R_SH_JMP_SLOT64 },
  { BFD_RELOC_SH_RELATIVE64, R_SH_RELATIVE64 },
  { BFD_RELOC_SH_GOT10BY4, R_SH_GOT10BY4 },
  { BFD_RELOC_SH_GOT10BY8, R_SH_GOT10BY8 },
  { BFD_RELOC_SH_GOTPLT10BY4, R_SH_GOTPLT10BY4 },
  { BFD_RELOC_SH_GOTPLT10BY8, R_SH_GOTPLT10BY8 },
  { BFD_RELOC_SH_PT_16, R_SH_PT_16 },
  { BFD_RELOC_SH_SHMEDIA_CODE, R_SH_SHMEDIA_CODE },
  { BFD_RELOC_SH_IMMU5, R_SH_DIR5U },
  { BFD_RELOC_SH_IMMS6, R_SH_DIR6S },
  { BFD_RELOC_SH_IMMU6, R_SH_DIR6U },
  { BFD_RELOC_SH_IMMS10, R_SH_DIR10S },
  { BFD_RELOC_SH_IMMS10BY2, R_SH_DIR10SW },
  { BFD_RELOC_SH_IMMS10BY4, R_SH_DIR10SL },
  { BFD_RELOC_SH_IMMS10BY8, R_SH_DIR10SQ },
  { BFD_RELOC_SH_IMMS16, R_SH_IMMS16 },
  { BFD_RELOC_SH_IMMU16, R_SH_IMMU16 },
  { BFD_RELOC_SH_IMM_LOW16, R_SH_IMM_LOW16 },
  { BFD_RELOC_SH_IMM_LOW16_PCREL, R_SH_IMM_LOW16_PCREL },
  { BFD_RELOC_SH_IMM_MEDLOW16, R_SH_IMM_MEDLOW16 },
  { BFD_RELOC_SH_IMM_MEDLOW16_PCREL, R_SH_IMM_MEDLOW16_PCREL },
  { BFD_RELOC_SH_IMM_MEDHI16, R_SH_IMM_MEDHI16 },
  { BFD_RELOC_SH_IMM_MEDHI16_PCREL, R_SH_IMM_MEDHI16_PCREL },
  { BFD_RELOC_SH_IMM_HI16, R_SH_IMM_HI16 },
  { BFD_RELOC_SH_IMM_HI16_PCREL, R_SH_IMM_HI16_PCREL },
  { BFD_RELOC_64, R_SH_64 },
  { BFD_RELOC_64_PCREL, R_SH_64_PCREL },
#endif /* not INCLUDE_SHMEDIA */
};

/* Given a BFD reloc code, return the howto structure for the
   corresponding SH ELF reloc.  */

static reloc_howto_type *
sh_elf_reloc_type_lookup (bfd *abfd, bfd_reloc_code_real_type code)
{
  unsigned int i;

  for (i = 0; i < sizeof (sh_reloc_map) / sizeof (struct elf_reloc_map); i++)
    {
      if (sh_reloc_map[i].bfd_reloc_val == code)
	return get_howto_table (abfd) + (int) sh_reloc_map[i].elf_reloc_val;
    }

  return NULL;
}

static reloc_howto_type *
sh_elf_reloc_name_lookup (bfd *abfd, const char *r_name)
{
  unsigned int i;

  if (vxworks_object_p (abfd))
    {
      for (i = 0;
	   i < (sizeof (sh_vxworks_howto_table)
		/ sizeof (sh_vxworks_howto_table[0]));
	   i++)
	if (sh_vxworks_howto_table[i].name != NULL
	    && strcasecmp (sh_vxworks_howto_table[i].name, r_name) == 0)
	  return &sh_vxworks_howto_table[i];
    }
  else
    {
      for (i = 0;
	   i < (sizeof (sh_elf_howto_table)
		/ sizeof (sh_elf_howto_table[0]));
	   i++)
	if (sh_elf_howto_table[i].name != NULL
	    && strcasecmp (sh_elf_howto_table[i].name, r_name) == 0)
	  return &sh_elf_howto_table[i];
    }

  return NULL;
}

/* Given an ELF reloc, fill in the howto field of a relent.  */

static void
sh_elf_info_to_howto (bfd *abfd, arelent *cache_ptr, Elf_Internal_Rela *dst)
{
  unsigned int r;

  r = ELF32_R_TYPE (dst->r_info);

  if (r >= R_SH_max
      || (r >= R_SH_FIRST_INVALID_RELOC   && r <= R_SH_LAST_INVALID_RELOC)
      || (r >= R_SH_FIRST_INVALID_RELOC_2 && r <= R_SH_LAST_INVALID_RELOC_2)
      || (r >= R_SH_FIRST_INVALID_RELOC_3 && r <= R_SH_LAST_INVALID_RELOC_3)
      || (r >= R_SH_FIRST_INVALID_RELOC_4 && r <= R_SH_LAST_INVALID_RELOC_4)
      || (r >= R_SH_FIRST_INVALID_RELOC_5 && r <= R_SH_LAST_INVALID_RELOC_5)
      || (r >= R_SH_FIRST_INVALID_RELOC_6 && r <= R_SH_LAST_INVALID_RELOC_6))
    {
      /* xgettext:c-format */
      _bfd_error_handler (_("%B: unrecognised SH reloc number: %d"),
			  abfd, r);
      bfd_set_error (bfd_error_bad_value);
      r = R_SH_NONE;
    }

  cache_ptr->howto = get_howto_table (abfd) + r;
}

/* This function handles relaxing for SH ELF.  See the corresponding
   function in coff-sh.c for a description of what this does.  FIXME:
   There is a lot of duplication here between this code and the COFF
   specific code.  The format of relocs and symbols is wound deeply
   into this code, but it would still be better if the duplication
   could be eliminated somehow.  Note in particular that although both
   functions use symbols like R_SH_CODE, those symbols have different
   values; in coff-sh.c they come from include/coff/sh.h, whereas here
   they come from enum elf_sh_reloc_type in include/elf/sh.h.  */

static bfd_boolean
sh_elf_relax_section (bfd *abfd, asection *sec,
		      struct bfd_link_info *link_info, bfd_boolean *again)
{
  Elf_Internal_Shdr *symtab_hdr;
  Elf_Internal_Rela *internal_relocs;
  bfd_boolean have_code;
  Elf_Internal_Rela *irel, *irelend;
  bfd_byte *contents = NULL;
  Elf_Internal_Sym *isymbuf = NULL;

  *again = FALSE;

  if (bfd_link_relocatable (link_info)
      || (sec->flags & SEC_RELOC) == 0
      || sec->reloc_count == 0)
    return TRUE;

#ifdef INCLUDE_SHMEDIA
  if (elf_section_data (sec)->this_hdr.sh_flags
      & (SHF_SH5_ISA32 | SHF_SH5_ISA32_MIXED))
    {
      return TRUE;
    }
#endif

  symtab_hdr = &elf_symtab_hdr (abfd);

  internal_relocs = (_bfd_elf_link_read_relocs
		     (abfd, sec, NULL, (Elf_Internal_Rela *) NULL,
		      link_info->keep_memory));
  if (internal_relocs == NULL)
    goto error_return;

  have_code = FALSE;

  irelend = internal_relocs + sec->reloc_count;
  for (irel = internal_relocs; irel < irelend; irel++)
    {
      bfd_vma laddr, paddr, symval;
      unsigned short insn;
      Elf_Internal_Rela *irelfn, *irelscan, *irelcount;
      bfd_signed_vma foff;

      if (ELF32_R_TYPE (irel->r_info) == (int) R_SH_CODE)
	have_code = TRUE;

      if (ELF32_R_TYPE (irel->r_info) != (int) R_SH_USES)
	continue;

      /* Get the section contents.  */
      if (contents == NULL)
	{
	  if (elf_section_data (sec)->this_hdr.contents != NULL)
	    contents = elf_section_data (sec)->this_hdr.contents;
	  else
	    {
	      if (!bfd_malloc_and_get_section (abfd, sec, &contents))
		goto error_return;
	    }
	}

      /* The r_addend field of the R_SH_USES reloc will point us to
	 the register load.  The 4 is because the r_addend field is
	 computed as though it were a jump offset, which are based
	 from 4 bytes after the jump instruction.  */
      laddr = irel->r_offset + 4 + irel->r_addend;
      if (laddr >= sec->size)
	{
	  /* xgettext:c-format */
	  _bfd_error_handler (_("%B: %#Lx: warning: bad R_SH_USES offset"),
			      abfd, irel->r_offset);
	  continue;
	}
      insn = bfd_get_16 (abfd, contents + laddr);

      /* If the instruction is not mov.l NN,rN, we don't know what to
	 do.  */
      if ((insn & 0xf000) != 0xd000)
	{
	  _bfd_error_handler
	    /* xgettext:c-format */
	    (_("%B: %#Lx: warning: R_SH_USES points to unrecognized insn 0x%x"),
	     abfd, irel->r_offset, insn);
	  continue;
	}

      /* Get the address from which the register is being loaded.  The
	 displacement in the mov.l instruction is quadrupled.  It is a
	 displacement from four bytes after the movl instruction, but,
	 before adding in the PC address, two least significant bits
	 of the PC are cleared.  We assume that the section is aligned
	 on a four byte boundary.  */
      paddr = insn & 0xff;
      paddr *= 4;
      paddr += (laddr + 4) &~ (bfd_vma) 3;
      if (paddr >= sec->size)
	{
	  _bfd_error_handler
	    /* xgettext:c-format */
	    (_("%B: %#Lx: warning: bad R_SH_USES load offset"),
	     abfd, irel->r_offset);
	  continue;
	}

      /* Get the reloc for the address from which the register is
	 being loaded.  This reloc will tell us which function is
	 actually being called.  */
      for (irelfn = internal_relocs; irelfn < irelend; irelfn++)
	if (irelfn->r_offset == paddr
	    && ELF32_R_TYPE (irelfn->r_info) == (int) R_SH_DIR32)
	  break;
      if (irelfn >= irelend)
	{
	  _bfd_error_handler
	    /* xgettext:c-format */
	    (_("%B: %#Lx: warning: could not find expected reloc"),
	     abfd, paddr);
	  continue;
	}

      /* Read this BFD's symbols if we haven't done so already.  */
      if (isymbuf == NULL && symtab_hdr->sh_info != 0)
	{
	  isymbuf = (Elf_Internal_Sym *) symtab_hdr->contents;
	  if (isymbuf == NULL)
	    isymbuf = bfd_elf_get_elf_syms (abfd, symtab_hdr,
					    symtab_hdr->sh_info, 0,
					    NULL, NULL, NULL);
	  if (isymbuf == NULL)
	    goto error_return;
	}

      /* Get the value of the symbol referred to by the reloc.  */
      if (ELF32_R_SYM (irelfn->r_info) < symtab_hdr->sh_info)
	{
	  /* A local symbol.  */
	  Elf_Internal_Sym *isym;

	  isym = isymbuf + ELF32_R_SYM (irelfn->r_info);
	  if (isym->st_shndx
	      != (unsigned int) _bfd_elf_section_from_bfd_section (abfd, sec))
	    {
	      _bfd_error_handler
		/* xgettext:c-format */
		(_("%B: %#Lx: warning: symbol in unexpected section"),
		 abfd, paddr);
	      continue;
	    }

	  symval = (isym->st_value
		    + sec->output_section->vma
		    + sec->output_offset);
	}
      else
	{
	  unsigned long indx;
	  struct elf_link_hash_entry *h;

	  indx = ELF32_R_SYM (irelfn->r_info) - symtab_hdr->sh_info;
	  h = elf_sym_hashes (abfd)[indx];
	  BFD_ASSERT (h != NULL);
	  if (h->root.type != bfd_link_hash_defined
	      && h->root.type != bfd_link_hash_defweak)
	    {
	      /* This appears to be a reference to an undefined
		 symbol.  Just ignore it--it will be caught by the
		 regular reloc processing.  */
	      continue;
	    }

	  symval = (h->root.u.def.value
		    + h->root.u.def.section->output_section->vma
		    + h->root.u.def.section->output_offset);
	}

      if (get_howto_table (abfd)[R_SH_DIR32].partial_inplace)
	symval += bfd_get_32 (abfd, contents + paddr);
      else
	symval += irelfn->r_addend;

      /* See if this function call can be shortened.  */
      foff = (symval
	      - (irel->r_offset
		 + sec->output_section->vma
		 + sec->output_offset
		 + 4));
      /* A branch to an address beyond ours might be increased by an
	 .align that doesn't move when bytes behind us are deleted.
	 So, we add some slop in this calculation to allow for
	 that.  */
      if (foff < -0x1000 || foff >= 0x1000 - 8)
	{
	  /* After all that work, we can't shorten this function call.  */
	  continue;
	}

      /* Shorten the function call.  */

      /* For simplicity of coding, we are going to modify the section
	 contents, the section relocs, and the BFD symbol table.  We
	 must tell the rest of the code not to free up this
	 information.  It would be possible to instead create a table
	 of changes which have to be made, as is done in coff-mips.c;
	 that would be more work, but would require less memory when
	 the linker is run.  */

      elf_section_data (sec)->relocs = internal_relocs;
      elf_section_data (sec)->this_hdr.contents = contents;
      symtab_hdr->contents = (unsigned char *) isymbuf;

      /* Replace the jmp/jsr with a bra/bsr.  */

      /* Change the R_SH_USES reloc into an R_SH_IND12W reloc, and
	 replace the jmp/jsr with a bra/bsr.  */
      irel->r_info = ELF32_R_INFO (ELF32_R_SYM (irelfn->r_info), R_SH_IND12W);
      /* We used to test (ELF32_R_SYM (irelfn->r_info) < symtab_hdr->sh_info)
	 here, but that only checks if the symbol is an external symbol,
	 not if the symbol is in a different section.  Besides, we need
	 a consistent meaning for the relocation, so we just assume here that
	 the value of the symbol is not available.  */

      /* We can't fully resolve this yet, because the external
	 symbol value may be changed by future relaxing.  We let
	 the final link phase handle it.  */
      if (bfd_get_16 (abfd, contents + irel->r_offset) & 0x0020)
	bfd_put_16 (abfd, (bfd_vma) 0xa000, contents + irel->r_offset);
      else
	bfd_put_16 (abfd, (bfd_vma) 0xb000, contents + irel->r_offset);

      irel->r_addend = -4;

      /* When we calculated the symbol "value" we had an offset in the
	 DIR32's word in memory (we read and add it above).  However,
	 the jsr we create does NOT have this offset encoded, so we
	 have to add it to the addend to preserve it.  */
      irel->r_addend += bfd_get_32 (abfd, contents + paddr);

      /* See if there is another R_SH_USES reloc referring to the same
	 register load.  */
      for (irelscan = internal_relocs; irelscan < irelend; irelscan++)
	if (ELF32_R_TYPE (irelscan->r_info) == (int) R_SH_USES
	    && laddr == irelscan->r_offset + 4 + irelscan->r_addend)
	  break;
      if (irelscan < irelend)
	{
	  /* Some other function call depends upon this register load,
	     and we have not yet converted that function call.
	     Indeed, we may never be able to convert it.  There is
	     nothing else we can do at this point.  */
	  continue;
	}

      /* Look for a R_SH_COUNT reloc on the location where the
	 function address is stored.  Do this before deleting any
	 bytes, to avoid confusion about the address.  */
      for (irelcount = internal_relocs; irelcount < irelend; irelcount++)
	if (irelcount->r_offset == paddr
	    && ELF32_R_TYPE (irelcount->r_info) == (int) R_SH_COUNT)
	  break;

      /* Delete the register load.  */
      if (! sh_elf_relax_delete_bytes (abfd, sec, laddr, 2))
	goto error_return;

      /* That will change things, so, just in case it permits some
	 other function call to come within range, we should relax
	 again.  Note that this is not required, and it may be slow.  */
      *again = TRUE;

      /* Now check whether we got a COUNT reloc.  */
      if (irelcount >= irelend)
	{
	  _bfd_error_handler
	    /* xgettext:c-format */
	    (_("%B: %#Lx: warning: could not find expected COUNT reloc"),
	     abfd, paddr);
	  continue;
	}

      /* The number of uses is stored in the r_addend field.  We've
	 just deleted one.  */
      if (irelcount->r_addend == 0)
	{
	  /* xgettext:c-format */
	  _bfd_error_handler (_("%B: %#Lx: warning: bad count"),
			      abfd, paddr);
	  continue;
	}

      --irelcount->r_addend;

      /* If there are no more uses, we can delete the address.  Reload
	 the address from irelfn, in case it was changed by the
	 previous call to sh_elf_relax_delete_bytes.  */
      if (irelcount->r_addend == 0)
	{
	  if (! sh_elf_relax_delete_bytes (abfd, sec, irelfn->r_offset, 4))
	    goto error_return;
	}

      /* We've done all we can with that function call.  */
    }

  /* Look for load and store instructions that we can align on four
     byte boundaries.  */
  if ((elf_elfheader (abfd)->e_flags & EF_SH_MACH_MASK) != EF_SH4
      && have_code)
    {
      bfd_boolean swapped;

      /* Get the section contents.  */
      if (contents == NULL)
	{
	  if (elf_section_data (sec)->this_hdr.contents != NULL)
	    contents = elf_section_data (sec)->this_hdr.contents;
	  else
	    {
	      if (!bfd_malloc_and_get_section (abfd, sec, &contents))
		goto error_return;
	    }
	}

      if (! sh_elf_align_loads (abfd, sec, internal_relocs, contents,
				&swapped))
	goto error_return;

      if (swapped)
	{
	  elf_section_data (sec)->relocs = internal_relocs;
	  elf_section_data (sec)->this_hdr.contents = contents;
	  symtab_hdr->contents = (unsigned char *) isymbuf;
	}
    }

  if (isymbuf != NULL
      && symtab_hdr->contents != (unsigned char *) isymbuf)
    {
      if (! link_info->keep_memory)
	free (isymbuf);
      else
	{
	  /* Cache the symbols for elf_link_input_bfd.  */
	  symtab_hdr->contents = (unsigned char *) isymbuf;
	}
    }

  if (contents != NULL
      && elf_section_data (sec)->this_hdr.contents != contents)
    {
      if (! link_info->keep_memory)
	free (contents);
      else
	{
	  /* Cache the section contents for elf_link_input_bfd.  */
	  elf_section_data (sec)->this_hdr.contents = contents;
	}
    }

  if (internal_relocs != NULL
      && elf_section_data (sec)->relocs != internal_relocs)
    free (internal_relocs);

  return TRUE;

 error_return:
  if (isymbuf != NULL
      && symtab_hdr->contents != (unsigned char *) isymbuf)
    free (isymbuf);
  if (contents != NULL
      && elf_section_data (sec)->this_hdr.contents != contents)
    free (contents);
  if (internal_relocs != NULL
      && elf_section_data (sec)->relocs != internal_relocs)
    free (internal_relocs);

  return FALSE;
}

/* Delete some bytes from a section while relaxing.  FIXME: There is a
   lot of duplication between this function and sh_relax_delete_bytes
   in coff-sh.c.  */

static bfd_boolean
sh_elf_relax_delete_bytes (bfd *abfd, asection *sec, bfd_vma addr,
			   int count)
{
  Elf_Internal_Shdr *symtab_hdr;
  unsigned int sec_shndx;
  bfd_byte *contents;
  Elf_Internal_Rela *irel, *irelend;
  Elf_Internal_Rela *irelalign;
  bfd_vma toaddr;
  Elf_Internal_Sym *isymbuf, *isym, *isymend;
  struct elf_link_hash_entry **sym_hashes;
  struct elf_link_hash_entry **end_hashes;
  unsigned int symcount;
  asection *o;

  symtab_hdr = &elf_symtab_hdr (abfd);
  isymbuf = (Elf_Internal_Sym *) symtab_hdr->contents;

  sec_shndx = _bfd_elf_section_from_bfd_section (abfd, sec);

  contents = elf_section_data (sec)->this_hdr.contents;

  /* The deletion must stop at the next ALIGN reloc for an alignment
     power larger than the number of bytes we are deleting.  */

  irelalign = NULL;
  toaddr = sec->size;

  irel = elf_section_data (sec)->relocs;
  irelend = irel + sec->reloc_count;
  for (; irel < irelend; irel++)
    {
      if (ELF32_R_TYPE (irel->r_info) == (int) R_SH_ALIGN
	  && irel->r_offset > addr
	  && count < (1 << irel->r_addend))
	{
	  irelalign = irel;
	  toaddr = irel->r_offset;
	  break;
	}
    }

  /* Actually delete the bytes.  */
  memmove (contents + addr, contents + addr + count,
	   (size_t) (toaddr - addr - count));
  if (irelalign == NULL)
    sec->size -= count;
  else
    {
      int i;

#define NOP_OPCODE (0x0009)

      BFD_ASSERT ((count & 1) == 0);
      for (i = 0; i < count; i += 2)
	bfd_put_16 (abfd, (bfd_vma) NOP_OPCODE, contents + toaddr - count + i);
    }

  /* Adjust all the relocs.  */
  for (irel = elf_section_data (sec)->relocs; irel < irelend; irel++)
    {
      bfd_vma nraddr, stop;
      bfd_vma start = 0;
      int insn = 0;
      int off, adjust, oinsn;
      bfd_signed_vma voff = 0;
      bfd_boolean overflow;

      /* Get the new reloc address.  */
      nraddr = irel->r_offset;
      if ((irel->r_offset > addr
	   && irel->r_offset < toaddr)
	  || (ELF32_R_TYPE (irel->r_info) == (int) R_SH_ALIGN
	      && irel->r_offset == toaddr))
	nraddr -= count;

      /* See if this reloc was for the bytes we have deleted, in which
	 case we no longer care about it.  Don't delete relocs which
	 represent addresses, though.  */
      if (irel->r_offset >= addr
	  && irel->r_offset < addr + count
	  && ELF32_R_TYPE (irel->r_info) != (int) R_SH_ALIGN
	  && ELF32_R_TYPE (irel->r_info) != (int) R_SH_CODE
	  && ELF32_R_TYPE (irel->r_info) != (int) R_SH_DATA
	  && ELF32_R_TYPE (irel->r_info) != (int) R_SH_LABEL)
	irel->r_info = ELF32_R_INFO (ELF32_R_SYM (irel->r_info),
				     (int) R_SH_NONE);

      /* If this is a PC relative reloc, see if the range it covers
	 includes the bytes we have deleted.  */
      switch ((enum elf_sh_reloc_type) ELF32_R_TYPE (irel->r_info))
	{
	default:
	  break;

	case R_SH_DIR8WPN:
	case R_SH_IND12W:
	case R_SH_DIR8WPZ:
	case R_SH_DIR8WPL:
	  start = irel->r_offset;
	  insn = bfd_get_16 (abfd, contents + nraddr);
	  break;
	}

      switch ((enum elf_sh_reloc_type) ELF32_R_TYPE (irel->r_info))
	{
	default:
	  start = stop = addr;
	  break;

	case R_SH_DIR32:
	  /* If this reloc is against a symbol defined in this
	     section, and the symbol will not be adjusted below, we
	     must check the addend to see it will put the value in
	     range to be adjusted, and hence must be changed.  */
	  if (ELF32_R_SYM (irel->r_info) < symtab_hdr->sh_info)
	    {
	      isym = isymbuf + ELF32_R_SYM (irel->r_info);
	      if (isym->st_shndx == sec_shndx
		  && (isym->st_value <= addr
		      || isym->st_value >= toaddr))
		{
		  bfd_vma val;

		  if (get_howto_table (abfd)[R_SH_DIR32].partial_inplace)
		    {
		      val = bfd_get_32 (abfd, contents + nraddr);
		      val += isym->st_value;
		      if (val > addr && val < toaddr)
			bfd_put_32 (abfd, val - count, contents + nraddr);
		    }
		  else
		    {
		      val = isym->st_value + irel->r_addend;
		      if (val > addr && val < toaddr)
			irel->r_addend -= count;
		    }
		}
	    }
	  start = stop = addr;
	  break;

	case R_SH_DIR8WPN:
	  off = insn & 0xff;
	  if (off & 0x80)
	    off -= 0x100;
	  stop = (bfd_vma) ((bfd_signed_vma) start + 4 + off * 2);
	  break;

	case R_SH_IND12W:
	  off = insn & 0xfff;
	  if (! off)
	    {
	      /* This has been made by previous relaxation.  Since the
		 relocation will be against an external symbol, the
		 final relocation will just do the right thing.  */
	      start = stop = addr;
	    }
	  else
	    {
	      if (off & 0x800)
		off -= 0x1000;
	      stop = (bfd_vma) ((bfd_signed_vma) start + 4 + off * 2);

	      /* The addend will be against the section symbol, thus
		 for adjusting the addend, the relevant start is the
		 start of the section.
		 N.B. If we want to abandon in-place changes here and
		 test directly using symbol + addend, we have to take into
		 account that the addend has already been adjusted by -4.  */
	      if (stop > addr && stop < toaddr)
		irel->r_addend -= count;
	    }
	  break;

	case R_SH_DIR8WPZ:
	  off = insn & 0xff;
	  stop = start + 4 + off * 2;
	  break;

	case R_SH_DIR8WPL:
	  off = insn & 0xff;
	  stop = (start & ~(bfd_vma) 3) + 4 + off * 4;
	  break;

	case R_SH_SWITCH8:
	case R_SH_SWITCH16:
	case R_SH_SWITCH32:
	  /* These relocs types represent
	       .word L2-L1
	     The r_addend field holds the difference between the reloc
	     address and L1.  That is the start of the reloc, and
	     adding in the contents gives us the top.  We must adjust
	     both the r_offset field and the section contents.
	     N.B. in gas / coff bfd, the elf bfd r_addend is called r_offset,
	     and the elf bfd r_offset is called r_vaddr.  */

	  stop = irel->r_offset;
	  start = (bfd_vma) ((bfd_signed_vma) stop - (long) irel->r_addend);

	  if (start > addr
	      && start < toaddr
	      && (stop <= addr || stop >= toaddr))
	    irel->r_addend += count;
	  else if (stop > addr
		   && stop < toaddr
		   && (start <= addr || start >= toaddr))
	    irel->r_addend -= count;

	  if (ELF32_R_TYPE (irel->r_info) == (int) R_SH_SWITCH16)
	    voff = bfd_get_signed_16 (abfd, contents + nraddr);
	  else if (ELF32_R_TYPE (irel->r_info) == (int) R_SH_SWITCH8)
	    voff = bfd_get_8 (abfd, contents + nraddr);
	  else
	    voff = bfd_get_signed_32 (abfd, contents + nraddr);
	  stop = (bfd_vma) ((bfd_signed_vma) start + voff);

	  break;

	case R_SH_USES:
	  start = irel->r_offset;
	  stop = (bfd_vma) ((bfd_signed_vma) start
			    + (long) irel->r_addend
			    + 4);
	  break;
	}

      if (start > addr
	  && start < toaddr
	  && (stop <= addr || stop >= toaddr))
	adjust = count;
      else if (stop > addr
	       && stop < toaddr
	       && (start <= addr || start >= toaddr))
	adjust = - count;
      else
	adjust = 0;

      if (adjust != 0)
	{
	  oinsn = insn;
	  overflow = FALSE;
	  switch ((enum elf_sh_reloc_type) ELF32_R_TYPE (irel->r_info))
	    {
	    default:
	      abort ();
	      break;

	    case R_SH_DIR8WPN:
	    case R_SH_DIR8WPZ:
	      insn += adjust / 2;
	      if ((oinsn & 0xff00) != (insn & 0xff00))
		overflow = TRUE;
	      bfd_put_16 (abfd, (bfd_vma) insn, contents + nraddr);
	      break;

	    case R_SH_IND12W:
	      insn += adjust / 2;
	      if ((oinsn & 0xf000) != (insn & 0xf000))
		overflow = TRUE;
	      bfd_put_16 (abfd, (bfd_vma) insn, contents + nraddr);
	      break;

	    case R_SH_DIR8WPL:
	      BFD_ASSERT (adjust == count || count >= 4);
	      if (count >= 4)
		insn += adjust / 4;
	      else
		{
		  if ((irel->r_offset & 3) == 0)
		    ++insn;
		}
	      if ((oinsn & 0xff00) != (insn & 0xff00))
		overflow = TRUE;
	      bfd_put_16 (abfd, (bfd_vma) insn, contents + nraddr);
	      break;

	    case R_SH_SWITCH8:
	      voff += adjust;
	      if (voff < 0 || voff >= 0xff)
		overflow = TRUE;
	      bfd_put_8 (abfd, voff, contents + nraddr);
	      break;

	    case R_SH_SWITCH16:
	      voff += adjust;
	      if (voff < - 0x8000 || voff >= 0x8000)
		overflow = TRUE;
	      bfd_put_signed_16 (abfd, (bfd_vma) voff, contents + nraddr);
	      break;

	    case R_SH_SWITCH32:
	      voff += adjust;
	      bfd_put_signed_32 (abfd, (bfd_vma) voff, contents + nraddr);
	      break;

	    case R_SH_USES:
	      irel->r_addend += adjust;
	      break;
	    }

	  if (overflow)
	    {
	      _bfd_error_handler
		/* xgettext:c-format */
		(_("%B: %#Lx: fatal: reloc overflow while relaxing"),
		 abfd, irel->r_offset);
	      bfd_set_error (bfd_error_bad_value);
	      return FALSE;
	    }
	}

      irel->r_offset = nraddr;
    }

  /* Look through all the other sections.  If there contain any IMM32
     relocs against internal symbols which we are not going to adjust
     below, we may need to adjust the addends.  */
  for (o = abfd->sections; o != NULL; o = o->next)
    {
      Elf_Internal_Rela *internal_relocs;
      Elf_Internal_Rela *irelscan, *irelscanend;
      bfd_byte *ocontents;

      if (o == sec
	  || (o->flags & SEC_RELOC) == 0
	  || o->reloc_count == 0)
	continue;

      /* We always cache the relocs.  Perhaps, if info->keep_memory is
	 FALSE, we should free them, if we are permitted to, when we
	 leave sh_coff_relax_section.  */
      internal_relocs = (_bfd_elf_link_read_relocs
			 (abfd, o, NULL, (Elf_Internal_Rela *) NULL, TRUE));
      if (internal_relocs == NULL)
	return FALSE;

      ocontents = NULL;
      irelscanend = internal_relocs + o->reloc_count;
      for (irelscan = internal_relocs; irelscan < irelscanend; irelscan++)
	{
	  /* Dwarf line numbers use R_SH_SWITCH32 relocs.  */
	  if (ELF32_R_TYPE (irelscan->r_info) == (int) R_SH_SWITCH32)
	    {
	      bfd_vma start, stop;
	      bfd_signed_vma voff;

	      if (ocontents == NULL)
		{
		  if (elf_section_data (o)->this_hdr.contents != NULL)
		    ocontents = elf_section_data (o)->this_hdr.contents;
		  else
		    {
		      /* We always cache the section contents.
			 Perhaps, if info->keep_memory is FALSE, we
			 should free them, if we are permitted to,
			 when we leave sh_coff_relax_section.  */
		      if (!bfd_malloc_and_get_section (abfd, o, &ocontents))
			{
			  if (ocontents != NULL)
			    free (ocontents);
			  return FALSE;
			}

		      elf_section_data (o)->this_hdr.contents = ocontents;
		    }
		}

	      stop = irelscan->r_offset;
	      start
		= (bfd_vma) ((bfd_signed_vma) stop - (long) irelscan->r_addend);

	      /* STOP is in a different section, so it won't change.  */
	      if (start > addr && start < toaddr)
		irelscan->r_addend += count;

	      voff = bfd_get_signed_32 (abfd, ocontents + irelscan->r_offset);
	      stop = (bfd_vma) ((bfd_signed_vma) start + voff);

	      if (start > addr
		  && start < toaddr
		  && (stop <= addr || stop >= toaddr))
		bfd_put_signed_32 (abfd, (bfd_vma) voff + count,
				   ocontents + irelscan->r_offset);
	      else if (stop > addr
		       && stop < toaddr
		       && (start <= addr || start >= toaddr))
		bfd_put_signed_32 (abfd, (bfd_vma) voff - count,
				   ocontents + irelscan->r_offset);
	    }

	  if (ELF32_R_TYPE (irelscan->r_info) != (int) R_SH_DIR32)
	    continue;

	  if (ELF32_R_SYM (irelscan->r_info) >= symtab_hdr->sh_info)
	    continue;


	  isym = isymbuf + ELF32_R_SYM (irelscan->r_info);
	  if (isym->st_shndx == sec_shndx
	      && (isym->st_value <= addr
		  || isym->st_value >= toaddr))
	    {
	      bfd_vma val;

	      if (ocontents == NULL)
		{
		  if (elf_section_data (o)->this_hdr.contents != NULL)
		    ocontents = elf_section_data (o)->this_hdr.contents;
		  else
		    {
		      /* We always cache the section contents.
			 Perhaps, if info->keep_memory is FALSE, we
			 should free them, if we are permitted to,
			 when we leave sh_coff_relax_section.  */
		      if (!bfd_malloc_and_get_section (abfd, o, &ocontents))
			{
			  if (ocontents != NULL)
			    free (ocontents);
			  return FALSE;
			}

		      elf_section_data (o)->this_hdr.contents = ocontents;
		    }
		}

	      val = bfd_get_32 (abfd, ocontents + irelscan->r_offset);
	      val += isym->st_value;
	      if (val > addr && val < toaddr)
		bfd_put_32 (abfd, val - count,
			    ocontents + irelscan->r_offset);
	    }
	}
    }

  /* Adjust the local symbols defined in this section.  */
  isymend = isymbuf + symtab_hdr->sh_info;
  for (isym = isymbuf; isym < isymend; isym++)
    {
      if (isym->st_shndx == sec_shndx
	  && isym->st_value > addr
	  && isym->st_value < toaddr)
	isym->st_value -= count;
    }

  /* Now adjust the global symbols defined in this section.  */
  symcount = (symtab_hdr->sh_size / sizeof (Elf32_External_Sym)
	      - symtab_hdr->sh_info);
  sym_hashes = elf_sym_hashes (abfd);
  end_hashes = sym_hashes + symcount;
  for (; sym_hashes < end_hashes; sym_hashes++)
    {
      struct elf_link_hash_entry *sym_hash = *sym_hashes;
      if ((sym_hash->root.type == bfd_link_hash_defined
	   || sym_hash->root.type == bfd_link_hash_defweak)
	  && sym_hash->root.u.def.section == sec
	  && sym_hash->root.u.def.value > addr
	  && sym_hash->root.u.def.value < toaddr)
	{
	  sym_hash->root.u.def.value -= count;
	}
    }

  /* See if we can move the ALIGN reloc forward.  We have adjusted
     r_offset for it already.  */
  if (irelalign != NULL)
    {
      bfd_vma alignto, alignaddr;

      alignto = BFD_ALIGN (toaddr, 1 << irelalign->r_addend);
      alignaddr = BFD_ALIGN (irelalign->r_offset,
			     1 << irelalign->r_addend);
      if (alignto != alignaddr)
	{
	  /* Tail recursion.  */
	  return sh_elf_relax_delete_bytes (abfd, sec, alignaddr,
					    (int) (alignto - alignaddr));
	}
    }

  return TRUE;
}

/* Look for loads and stores which we can align to four byte
   boundaries.  This is like sh_align_loads in coff-sh.c.  */

static bfd_boolean
sh_elf_align_loads (bfd *abfd ATTRIBUTE_UNUSED, asection *sec,
		    Elf_Internal_Rela *internal_relocs,
		    bfd_byte *contents ATTRIBUTE_UNUSED,
		    bfd_boolean *pswapped)
{
  Elf_Internal_Rela *irel, *irelend;
  bfd_vma *labels = NULL;
  bfd_vma *label, *label_end;
  bfd_size_type amt;

  *pswapped = FALSE;

  irelend = internal_relocs + sec->reloc_count;

  /* Get all the addresses with labels on them.  */
  amt = sec->reloc_count;
  amt *= sizeof (bfd_vma);
  labels = (bfd_vma *) bfd_malloc (amt);
  if (labels == NULL)
    goto error_return;
  label_end = labels;
  for (irel = internal_relocs; irel < irelend; irel++)
    {
      if (ELF32_R_TYPE (irel->r_info) == (int) R_SH_LABEL)
	{
	  *label_end = irel->r_offset;
	  ++label_end;
	}
    }

  /* Note that the assembler currently always outputs relocs in
     address order.  If that ever changes, this code will need to sort
     the label values and the relocs.  */

  label = labels;

  for (irel = internal_relocs; irel < irelend; irel++)
    {
      bfd_vma start, stop;

      if (ELF32_R_TYPE (irel->r_info) != (int) R_SH_CODE)
	continue;

      start = irel->r_offset;

      for (irel++; irel < irelend; irel++)
	if (ELF32_R_TYPE (irel->r_info) == (int) R_SH_DATA)
	  break;
      if (irel < irelend)
	stop = irel->r_offset;
      else
	stop = sec->size;

      if (! _bfd_sh_align_load_span (abfd, sec, contents, sh_elf_swap_insns,
				     internal_relocs, &label,
				     label_end, start, stop, pswapped))
	goto error_return;
    }

  free (labels);

  return TRUE;

 error_return:
  if (labels != NULL)
    free (labels);
  return FALSE;
}

#ifndef SH64_ELF
/* Swap two SH instructions.  This is like sh_swap_insns in coff-sh.c.  */

static bfd_boolean
sh_elf_swap_insns (bfd *abfd, asection *sec, void *relocs,
		   bfd_byte *contents, bfd_vma addr)
{
  Elf_Internal_Rela *internal_relocs = (Elf_Internal_Rela *) relocs;
  unsigned short i1, i2;
  Elf_Internal_Rela *irel, *irelend;

  /* Swap the instructions themselves.  */
  i1 = bfd_get_16 (abfd, contents + addr);
  i2 = bfd_get_16 (abfd, contents + addr + 2);
  bfd_put_16 (abfd, (bfd_vma) i2, contents + addr);
  bfd_put_16 (abfd, (bfd_vma) i1, contents + addr + 2);

  /* Adjust all reloc addresses.  */
  irelend = internal_relocs + sec->reloc_count;
  for (irel = internal_relocs; irel < irelend; irel++)
    {
      enum elf_sh_reloc_type type;
      int add;

      /* There are a few special types of relocs that we don't want to
	 adjust.  These relocs do not apply to the instruction itself,
	 but are only associated with the address.  */
      type = (enum elf_sh_reloc_type) ELF32_R_TYPE (irel->r_info);
      if (type == R_SH_ALIGN
	  || type == R_SH_CODE
	  || type == R_SH_DATA
	  || type == R_SH_LABEL)
	continue;

      /* If an R_SH_USES reloc points to one of the addresses being
	 swapped, we must adjust it.  It would be incorrect to do this
	 for a jump, though, since we want to execute both
	 instructions after the jump.  (We have avoided swapping
	 around a label, so the jump will not wind up executing an
	 instruction it shouldn't).  */
      if (type == R_SH_USES)
	{
	  bfd_vma off;

	  off = irel->r_offset + 4 + irel->r_addend;
	  if (off == addr)
	    irel->r_offset += 2;
	  else if (off == addr + 2)
	    irel->r_offset -= 2;
	}

      if (irel->r_offset == addr)
	{
	  irel->r_offset += 2;
	  add = -2;
	}
      else if (irel->r_offset == addr + 2)
	{
	  irel->r_offset -= 2;
	  add = 2;
	}
      else
	add = 0;

      if (add != 0)
	{
	  bfd_byte *loc;
	  unsigned short insn, oinsn;
	  bfd_boolean overflow;

	  loc = contents + irel->r_offset;
	  overflow = FALSE;
	  switch (type)
	    {
	    default:
	      break;

	    case R_SH_DIR8WPN:
	    case R_SH_DIR8WPZ:
	      insn = bfd_get_16 (abfd, loc);
	      oinsn = insn;
	      insn += add / 2;
	      if ((oinsn & 0xff00) != (insn & 0xff00))
		overflow = TRUE;
	      bfd_put_16 (abfd, (bfd_vma) insn, loc);
	      break;

	    case R_SH_IND12W:
	      insn = bfd_get_16 (abfd, loc);
	      oinsn = insn;
	      insn += add / 2;
	      if ((oinsn & 0xf000) != (insn & 0xf000))
		overflow = TRUE;
	      bfd_put_16 (abfd, (bfd_vma) insn, loc);
	      break;

	    case R_SH_DIR8WPL:
	      /* This reloc ignores the least significant 3 bits of
		 the program counter before adding in the offset.
		 This means that if ADDR is at an even address, the
		 swap will not affect the offset.  If ADDR is an at an
		 odd address, then the instruction will be crossing a
		 four byte boundary, and must be adjusted.  */
	      if ((addr & 3) != 0)
		{
		  insn = bfd_get_16 (abfd, loc);
		  oinsn = insn;
		  insn += add / 2;
		  if ((oinsn & 0xff00) != (insn & 0xff00))
		    overflow = TRUE;
		  bfd_put_16 (abfd, (bfd_vma) insn, loc);
		}

	      break;
	    }

	  if (overflow)
	    {
	      _bfd_error_handler
		/* xgettext:c-format */
		(_("%B: %#Lx: fatal: reloc overflow while relaxing"),
		 abfd, irel->r_offset);
	      bfd_set_error (bfd_error_bad_value);
	      return FALSE;
	    }
	}
    }

  return TRUE;
}
#endif /* defined SH64_ELF */

/* Describes one of the various PLT styles.  */

struct elf_sh_plt_info
{
  /* The template for the first PLT entry, or NULL if there is no special
     first entry.  */
  const bfd_byte *plt0_entry;

  /* The size of PLT0_ENTRY in bytes, or 0 if PLT0_ENTRY is NULL.  */
  bfd_vma plt0_entry_size;

  /* Index I is the offset into PLT0_ENTRY of a pointer to
     _GLOBAL_OFFSET_TABLE_ + I * 4.  The value is MINUS_ONE
     if there is no such pointer.  */
  bfd_vma plt0_got_fields[3];

  /* The template for a symbol's PLT entry.  */
  const bfd_byte *symbol_entry;

  /* The size of SYMBOL_ENTRY in bytes.  */
  bfd_vma symbol_entry_size;

  /* Byte offsets of fields in SYMBOL_ENTRY.  Not all fields are used
     on all targets.  The comments by each member indicate the value
     that the field must hold.  */
  struct {
    bfd_vma got_entry; /* the address of the symbol's .got.plt entry */
    bfd_vma plt; /* .plt (or a branch to .plt on VxWorks) */
    bfd_vma reloc_offset; /* the offset of the symbol's JMP_SLOT reloc */
    bfd_boolean got20; /* TRUE if got_entry points to a movi20
			  instruction (instead of a constant pool
			  entry).  */
  } symbol_fields;

  /* The offset of the resolver stub from the start of SYMBOL_ENTRY.  */
  bfd_vma symbol_resolve_offset;

  /* A different PLT layout which can be used for the first
     MAX_SHORT_PLT entries.  It must share the same plt0.  NULL in
     other cases.  */
  const struct elf_sh_plt_info *short_plt;
};

#ifdef INCLUDE_SHMEDIA

/* The size in bytes of an entry in the procedure linkage table.  */

#define ELF_PLT_ENTRY_SIZE 64

/* First entry in an absolute procedure linkage table look like this.  */

static const bfd_byte elf_sh_plt0_entry_be[ELF_PLT_ENTRY_SIZE] =
{
  0xcc, 0x00, 0x01, 0x10, /* movi  .got.plt >> 16, r17 */
  0xc8, 0x00, 0x01, 0x10, /* shori .got.plt & 65535, r17 */
  0x89, 0x10, 0x09, 0x90, /* ld.l  r17, 8, r25 */
  0x6b, 0xf1, 0x66, 0x00, /* ptabs r25, tr0 */
  0x89, 0x10, 0x05, 0x10, /* ld.l  r17, 4, r17 */
  0x44, 0x01, 0xff, 0xf0, /* blink tr0, r63 */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
};

static const bfd_byte elf_sh_plt0_entry_le[ELF_PLT_ENTRY_SIZE] =
{
  0x10, 0x01, 0x00, 0xcc, /* movi  .got.plt >> 16, r17 */
  0x10, 0x01, 0x00, 0xc8, /* shori .got.plt & 65535, r17 */
  0x90, 0x09, 0x10, 0x89, /* ld.l  r17, 8, r25 */
  0x00, 0x66, 0xf1, 0x6b, /* ptabs r25, tr0 */
  0x10, 0x05, 0x10, 0x89, /* ld.l  r17, 4, r17 */
  0xf0, 0xff, 0x01, 0x44, /* blink tr0, r63 */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
};

/* Sebsequent entries in an absolute procedure linkage table look like
   this.  */

static const bfd_byte elf_sh_plt_entry_be[ELF_PLT_ENTRY_SIZE] =
{
  0xcc, 0x00, 0x01, 0x90, /* movi  nameN-in-GOT >> 16, r25 */
  0xc8, 0x00, 0x01, 0x90, /* shori nameN-in-GOT & 65535, r25 */
  0x89, 0x90, 0x01, 0x90, /* ld.l  r25, 0, r25 */
  0x6b, 0xf1, 0x66, 0x00, /* ptabs r25, tr0 */
  0x44, 0x01, 0xff, 0xf0, /* blink tr0, r63 */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0xcc, 0x00, 0x01, 0x90, /* movi  .PLT0 >> 16, r25 */
  0xc8, 0x00, 0x01, 0x90, /* shori .PLT0 & 65535, r25 */
  0x6b, 0xf1, 0x66, 0x00, /* ptabs r25, tr0 */
  0xcc, 0x00, 0x01, 0x50, /* movi  reloc-offset >> 16, r21 */
  0xc8, 0x00, 0x01, 0x50, /* shori reloc-offset & 65535, r21 */
  0x44, 0x01, 0xff, 0xf0, /* blink tr0, r63 */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
};

static const bfd_byte elf_sh_plt_entry_le[ELF_PLT_ENTRY_SIZE] =
{
  0x90, 0x01, 0x00, 0xcc, /* movi  nameN-in-GOT >> 16, r25 */
  0x90, 0x01, 0x00, 0xc8, /* shori nameN-in-GOT & 65535, r25 */
  0x90, 0x01, 0x90, 0x89, /* ld.l  r25, 0, r25 */
  0x00, 0x66, 0xf1, 0x6b, /* ptabs r25, tr0 */
  0xf0, 0xff, 0x01, 0x44, /* blink tr0, r63 */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0x90, 0x01, 0x00, 0xcc, /* movi  .PLT0 >> 16, r25 */
  0x90, 0x01, 0x00, 0xc8, /* shori .PLT0 & 65535, r25 */
  0x00, 0x66, 0xf1, 0x6b, /* ptabs r25, tr0 */
  0x50, 0x01, 0x00, 0xcc, /* movi  reloc-offset >> 16, r21 */
  0x50, 0x01, 0x00, 0xc8, /* shori reloc-offset & 65535, r21 */
  0xf0, 0xff, 0x01, 0x44, /* blink tr0, r63 */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
};

/* Entries in a PIC procedure linkage table look like this.  */

static const bfd_byte elf_sh_pic_plt_entry_be[ELF_PLT_ENTRY_SIZE] =
{
  0xcc, 0x00, 0x01, 0x90, /* movi  nameN@GOT >> 16, r25 */
  0xc8, 0x00, 0x01, 0x90, /* shori nameN@GOT & 65535, r25 */
  0x40, 0xc2, 0x65, 0x90, /* ldx.l r12, r25, r25 */
  0x6b, 0xf1, 0x66, 0x00, /* ptabs r25, tr0 */
  0x44, 0x01, 0xff, 0xf0, /* blink tr0, r63 */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0x6f, 0xf0, 0xff, 0xf0, /* nop */
  0xce, 0x00, 0x01, 0x10, /* movi  -GOT_BIAS, r17 */
  0x00, 0xc8, 0x45, 0x10, /* add.l r12, r17, r17 */
  0x89, 0x10, 0x09, 0x90, /* ld.l  r17, 8, r25 */
  0x6b, 0xf1, 0x66, 0x00, /* ptabs r25, tr0 */
  0x89, 0x10, 0x05, 0x10, /* ld.l  r17, 4, r17 */
  0xcc, 0x00, 0x01, 0x50, /* movi  reloc-offset >> 16, r21 */
  0xc8, 0x00, 0x01, 0x50, /* shori reloc-offset & 65535, r21 */
  0x44, 0x01, 0xff, 0xf0, /* blink tr0, r63 */
};

static const bfd_byte elf_sh_pic_plt_entry_le[ELF_PLT_ENTRY_SIZE] =
{
  0x90, 0x01, 0x00, 0xcc, /* movi  nameN@GOT >> 16, r25 */
  0x90, 0x01, 0x00, 0xc8, /* shori nameN@GOT & 65535, r25 */
  0x90, 0x65, 0xc2, 0x40, /* ldx.l r12, r25, r25 */
  0x00, 0x66, 0xf1, 0x6b, /* ptabs r25, tr0 */
  0xf0, 0xff, 0x01, 0x44, /* blink tr0, r63 */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0xf0, 0xff, 0xf0, 0x6f, /* nop */
  0x10, 0x01, 0x00, 0xce, /* movi  -GOT_BIAS, r17 */
  0x10, 0x45, 0xc8, 0x00, /* add.l r12, r17, r17 */
  0x90, 0x09, 0x10, 0x89, /* ld.l  r17, 8, r25 */
  0x00, 0x66, 0xf1, 0x6b, /* ptabs r25, tr0 */
  0x10, 0x05, 0x10, 0x89, /* ld.l  r17, 4, r17 */
  0x50, 0x01, 0x00, 0xcc, /* movi  reloc-offset >> 16, r21 */
  0x50, 0x01, 0x00, 0xc8, /* shori reloc-offset & 65535, r21 */
  0xf0, 0xff, 0x01, 0x44, /* blink tr0, r63 */
};

static const struct elf_sh_plt_info elf_sh_plts[2][2] = {
  {
    {
      /* Big-endian non-PIC.  */
      elf_sh_plt0_entry_be,
      ELF_PLT_ENTRY_SIZE,
      { 0, MINUS_ONE, MINUS_ONE },
      elf_sh_plt_entry_be,
      ELF_PLT_ENTRY_SIZE,
      { 0, 32, 48, FALSE },
      33, /* includes ISA encoding */
      NULL
    },
    {
      /* Little-endian non-PIC.  */
      elf_sh_plt0_entry_le,
      ELF_PLT_ENTRY_SIZE,
      { 0, MINUS_ONE, MINUS_ONE },
      elf_sh_plt_entry_le,
      ELF_PLT_ENTRY_SIZE,
      { 0, 32, 48, FALSE },
      33, /* includes ISA encoding */
      NULL
    },
  },
  {
    {
      /* Big-endian PIC.  */
      elf_sh_plt0_entry_be,
      ELF_PLT_ENTRY_SIZE,
      { MINUS_ONE, MINUS_ONE, MINUS_ONE },
      elf_sh_pic_plt_entry_be,
      ELF_PLT_ENTRY_SIZE,
      { 0, MINUS_ONE, 52, FALSE },
      33, /* includes ISA encoding */
      NULL
    },
    {
      /* Little-endian PIC.  */
      elf_sh_plt0_entry_le,
      ELF_PLT_ENTRY_SIZE,
      { MINUS_ONE, MINUS_ONE, MINUS_ONE },
      elf_sh_pic_plt_entry_le,
      ELF_PLT_ENTRY_SIZE,
      { 0, MINUS_ONE, 52, FALSE },
      33, /* includes ISA encoding */
      NULL
    },
  }
};

/* Return offset of the linker in PLT0 entry.  */
#define elf_sh_plt0_gotplt_offset(info) 0

/* Install a 32-bit PLT field starting at ADDR, which occurs in OUTPUT_BFD.
   VALUE is the field's value and CODE_P is true if VALUE refers to code,
   not data.

   On SH64, each 32-bit field is loaded by a movi/shori pair.  */

inline static void
install_plt_field (bfd *output_bfd, bfd_boolean code_p,
		   unsigned long value, bfd_byte *addr)
{
  value |= code_p;
  bfd_put_32 (output_bfd,
	      bfd_get_32 (output_bfd, addr)
	      | ((value >> 6) & 0x3fffc00),
	      addr);
  bfd_put_32 (output_bfd,
	      bfd_get_32 (output_bfd, addr + 4)
	      | ((value << 10) & 0x3fffc00),
	      addr + 4);
}

/* Return the type of PLT associated with ABFD.  PIC_P is true if
   the object is position-independent.  */

static const struct elf_sh_plt_info *
get_plt_info (bfd *abfd ATTRIBUTE_UNUSED, bfd_boolean pic_p)
{
  return &elf_sh_plts[pic_p][!bfd_big_endian (abfd)];
}
#else
/* The size in bytes of an entry in the procedure linkage table.  */

#define ELF_PLT_ENTRY_SIZE 28

/* First entry in an absolute procedure linkage table look like this.  */

/* Note - this code has been "optimised" not to use r2.  r2 is used by
   GCC to return the address of large structures, so it should not be
   corrupted here.  This does mean however, that this PLT does not conform
   to the SH PIC ABI.  That spec says that r0 contains the type of the PLT
   and r2 contains the GOT id.  This version stores the GOT id in r0 and
   ignores the type.  Loaders can easily detect this difference however,
   since the type will always be 0 or 8, and the GOT ids will always be
   greater than or equal to 12.  */
static const bfd_byte elf_sh_plt0_entry_be[ELF_PLT_ENTRY_SIZE] =
{
  0xd0, 0x05,	/* mov.l 2f,r0 */
  0x60, 0x02,	/* mov.l @r0,r0 */
  0x2f, 0x06,	/* mov.l r0,@-r15 */
  0xd0, 0x03,	/* mov.l 1f,r0 */
  0x60, 0x02,	/* mov.l @r0,r0 */
  0x40, 0x2b,	/* jmp @r0 */
  0x60, 0xf6,	/*  mov.l @r15+,r0 */
  0x00, 0x09,	/* nop */
  0x00, 0x09,	/* nop */
  0x00, 0x09,	/* nop */
  0, 0, 0, 0,	/* 1: replaced with address of .got.plt + 8.  */
  0, 0, 0, 0,	/* 2: replaced with address of .got.plt + 4.  */
};

static const bfd_byte elf_sh_plt0_entry_le[ELF_PLT_ENTRY_SIZE] =
{
  0x05, 0xd0,	/* mov.l 2f,r0 */
  0x02, 0x60,	/* mov.l @r0,r0 */
  0x06, 0x2f,	/* mov.l r0,@-r15 */
  0x03, 0xd0,	/* mov.l 1f,r0 */
  0x02, 0x60,	/* mov.l @r0,r0 */
  0x2b, 0x40,	/* jmp @r0 */
  0xf6, 0x60,	/*  mov.l @r15+,r0 */
  0x09, 0x00,	/* nop */
  0x09, 0x00,	/* nop */
  0x09, 0x00,	/* nop */
  0, 0, 0, 0,	/* 1: replaced with address of .got.plt + 8.  */
  0, 0, 0, 0,	/* 2: replaced with address of .got.plt + 4.  */
};

/* Sebsequent entries in an absolute procedure linkage table look like
   this.  */

static const bfd_byte elf_sh_plt_entry_be[ELF_PLT_ENTRY_SIZE] =
{
  0xd0, 0x04,	/* mov.l 1f,r0 */
  0x60, 0x02,	/* mov.l @(r0,r12),r0 */
  0xd1, 0x02,	/* mov.l 0f,r1 */
  0x40, 0x2b,   /* jmp @r0 */
  0x60, 0x13,	/*  mov r1,r0 */
  0xd1, 0x03,	/* mov.l 2f,r1 */
  0x40, 0x2b,	/* jmp @r0 */
  0x00, 0x09,	/* nop */
  0, 0, 0, 0,	/* 0: replaced with address of .PLT0.  */
  0, 0, 0, 0,	/* 1: replaced with address of this symbol in .got.  */
  0, 0, 0, 0,	/* 2: replaced with offset into relocation table.  */
};

static const bfd_byte elf_sh_plt_entry_le[ELF_PLT_ENTRY_SIZE] =
{
  0x04, 0xd0,	/* mov.l 1f,r0 */
  0x02, 0x60,	/* mov.l @r0,r0 */
  0x02, 0xd1,	/* mov.l 0f,r1 */
  0x2b, 0x40,   /* jmp @r0 */
  0x13, 0x60,	/*  mov r1,r0 */
  0x03, 0xd1,	/* mov.l 2f,r1 */
  0x2b, 0x40,	/* jmp @r0 */
  0x09, 0x00,	/*  nop */
  0, 0, 0, 0,	/* 0: replaced with address of .PLT0.  */
  0, 0, 0, 0,	/* 1: replaced with address of this symbol in .got.  */
  0, 0, 0, 0,	/* 2: replaced with offset into relocation table.  */
};

/* Entries in a PIC procedure linkage table look like this.  */

static const bfd_byte elf_sh_pic_plt_entry_be[ELF_PLT_ENTRY_SIZE] =
{
  0xd0, 0x04,	/* mov.l 1f,r0 */
  0x00, 0xce,	/* mov.l @(r0,r12),r0 */
  0x40, 0x2b,	/* jmp @r0 */
  0x00, 0x09,	/*  nop */
  0x50, 0xc2,	/* mov.l @(8,r12),r0 */
  0xd1, 0x03,	/* mov.l 2f,r1 */
  0x40, 0x2b,	/* jmp @r0 */
  0x50, 0xc1,	/*  mov.l @(4,r12),r0 */
  0x00, 0x09,	/* nop */
  0x00, 0x09,	/* nop */
  0, 0, 0, 0,	/* 1: replaced with address of this symbol in .got.  */
  0, 0, 0, 0    /* 2: replaced with offset into relocation table.  */
};

static const bfd_byte elf_sh_pic_plt_entry_le[ELF_PLT_ENTRY_SIZE] =
{
  0x04, 0xd0,	/* mov.l 1f,r0 */
  0xce, 0x00,	/* mov.l @(r0,r12),r0 */
  0x2b, 0x40,	/* jmp @r0 */
  0x09, 0x00,	/*  nop */
  0xc2, 0x50,	/* mov.l @(8,r12),r0 */
  0x03, 0xd1,	/* mov.l 2f,r1 */
  0x2b, 0x40,	/* jmp @r0 */
  0xc1, 0x50,	/*  mov.l @(4,r12),r0 */
  0x09, 0x00,	/*  nop */
  0x09, 0x00,	/* nop */
  0, 0, 0, 0,	/* 1: replaced with address of this symbol in .got.  */
  0, 0, 0, 0    /* 2: replaced with offset into relocation table.  */
};

static const struct elf_sh_plt_info elf_sh_plts[2][2] = {
  {
    {
      /* Big-endian non-PIC.  */
      elf_sh_plt0_entry_be,
      ELF_PLT_ENTRY_SIZE,
      { MINUS_ONE, 24, 20 },
      elf_sh_plt_entry_be,
      ELF_PLT_ENTRY_SIZE,
      { 20, 16, 24, FALSE },
      8,
      NULL
    },
    {
      /* Little-endian non-PIC.  */
      elf_sh_plt0_entry_le,
      ELF_PLT_ENTRY_SIZE,
      { MINUS_ONE, 24, 20 },
      elf_sh_plt_entry_le,
      ELF_PLT_ENTRY_SIZE,
      { 20, 16, 24, FALSE },
      8,
      NULL
    },
  },
  {
    {
      /* Big-endian PIC.  */
      elf_sh_plt0_entry_be,
      ELF_PLT_ENTRY_SIZE,
      { MINUS_ONE, MINUS_ONE, MINUS_ONE },
      elf_sh_pic_plt_entry_be,
      ELF_PLT_ENTRY_SIZE,
      { 20, MINUS_ONE, 24, FALSE },
      8,
      NULL
    },
    {
      /* Little-endian PIC.  */
      elf_sh_plt0_entry_le,
      ELF_PLT_ENTRY_SIZE,
      { MINUS_ONE, MINUS_ONE, MINUS_ONE },
      elf_sh_pic_plt_entry_le,
      ELF_PLT_ENTRY_SIZE,
      { 20, MINUS_ONE, 24, FALSE },
      8,
      NULL
    },
  }
};

#define VXWORKS_PLT_HEADER_SIZE 12
#define VXWORKS_PLT_ENTRY_SIZE 24

static const bfd_byte vxworks_sh_plt0_entry_be[VXWORKS_PLT_HEADER_SIZE] =
{
  0xd1, 0x01,	/* mov.l @(8,pc),r1 */
  0x61, 0x12,	/* mov.l @r1,r1 */
  0x41, 0x2b,	/* jmp @r1 */
  0x00, 0x09,	/* nop */
  0, 0, 0, 0	/* 0: replaced with _GLOBAL_OFFSET_TABLE+8.  */
};

static const bfd_byte vxworks_sh_plt0_entry_le[VXWORKS_PLT_HEADER_SIZE] =
{
  0x01, 0xd1,	/* mov.l @(8,pc),r1 */
  0x12, 0x61,	/* mov.l @r1,r1 */
  0x2b, 0x41,	/* jmp @r1 */
  0x09, 0x00,	/* nop */
  0, 0, 0, 0	/* 0: replaced with _GLOBAL_OFFSET_TABLE+8.  */
};

static const bfd_byte vxworks_sh_plt_entry_be[VXWORKS_PLT_ENTRY_SIZE] =
{
  0xd0, 0x01,	/* mov.l @(8,pc),r0 */
  0x60, 0x02,	/* mov.l @r0,r0 */
  0x40, 0x2b,	/* jmp @r0 */
  0x00, 0x09,	/* nop */
  0, 0, 0, 0,	/* 0: replaced with address of this symbol in .got.  */
  0xd0, 0x01,	/* mov.l @(8,pc),r0 */
  0xa0, 0x00,	/* bra PLT (We need to fix the offset.)  */
  0x00, 0x09,	/* nop */
  0x00, 0x09,	/* nop */
  0, 0, 0, 0,	/* 1: replaced with offset into relocation table.  */
};

static const bfd_byte vxworks_sh_plt_entry_le[VXWORKS_PLT_ENTRY_SIZE] =
{
  0x01, 0xd0,	/* mov.l @(8,pc),r0 */
  0x02, 0x60,	/* mov.l @r0,r0 */
  0x2b, 0x40,	/* jmp @r0 */
  0x09, 0x00,	/* nop */
  0, 0, 0, 0,	/* 0: replaced with address of this symbol in .got.  */
  0x01, 0xd0,	/* mov.l @(8,pc),r0 */
  0x00, 0xa0,	/* bra PLT (We need to fix the offset.)  */
  0x09, 0x00,	/* nop */
  0x09, 0x00,	/* nop */
  0, 0, 0, 0,	/* 1: replaced with offset into relocation table.  */
};

static const bfd_byte vxworks_sh_pic_plt_entry_be[VXWORKS_PLT_ENTRY_SIZE] =
{
  0xd0, 0x01,	/* mov.l @(8,pc),r0 */
  0x00, 0xce,	/* mov.l @(r0,r12),r0 */
  0x40, 0x2b,	/* jmp @r0 */
  0x00, 0x09,	/* nop */
  0, 0, 0, 0,	/* 0: replaced with offset of this symbol in .got.  */
  0xd0, 0x01,	/* mov.l @(8,pc),r0 */
  0x51, 0xc2,	/* mov.l @(8,r12),r1 */
  0x41, 0x2b,	/* jmp @r1 */
  0x00, 0x09,	/* nop */
  0, 0, 0, 0,	/* 1: replaced with offset into relocation table.  */
};

static const bfd_byte vxworks_sh_pic_plt_entry_le[VXWORKS_PLT_ENTRY_SIZE] =
{
  0x01, 0xd0,	/* mov.l @(8,pc),r0 */
  0xce, 0x00,	/* mov.l @(r0,r12),r0 */
  0x2b, 0x40,	/* jmp @r0 */
  0x09, 0x00,	/* nop */
  0, 0, 0, 0,	/* 0: replaced with offset of this symbol in .got.  */
  0x01, 0xd0,	/* mov.l @(8,pc),r0 */
  0xc2, 0x51,	/* mov.l @(8,r12),r1 */
  0x2b, 0x41,	/* jmp @r1 */
  0x09, 0x00,	/* nop */
  0, 0, 0, 0,	/* 1: replaced with offset into relocation table.  */
};

static const struct elf_sh_plt_info vxworks_sh_plts[2][2] = {
  {
    {
      /* Big-endian non-PIC.  */
      vxworks_sh_plt0_entry_be,
      VXWORKS_PLT_HEADER_SIZE,
      { MINUS_ONE, MINUS_ONE, 8 },
      vxworks_sh_plt_entry_be,
      VXWORKS_PLT_ENTRY_SIZE,
      { 8, 14, 20, FALSE },
      12,
      NULL
    },
    {
      /* Little-endian non-PIC.  */
      vxworks_sh_plt0_entry_le,
      VXWORKS_PLT_HEADER_SIZE,
      { MINUS_ONE, MINUS_ONE, 8 },
      vxworks_sh_plt_entry_le,
      VXWORKS_PLT_ENTRY_SIZE,
      { 8, 14, 20, FALSE },
      12,
      NULL
    },
  },
  {
    {
      /* Big-endian PIC.  */
      NULL,
      0,
      { MINUS_ONE, MINUS_ONE, MINUS_ONE },
      vxworks_sh_pic_plt_entry_be,
      VXWORKS_PLT_ENTRY_SIZE,
      { 8, MINUS_ONE, 20, FALSE },
      12,
      NULL
    },
    {
      /* Little-endian PIC.  */
      NULL,
      0,
      { MINUS_ONE, MINUS_ONE, MINUS_ONE },
      vxworks_sh_pic_plt_entry_le,
      VXWORKS_PLT_ENTRY_SIZE,
      { 8, MINUS_ONE, 20, FALSE },
      12,
      NULL
    },
  }
};

/* FDPIC PLT entries.  Two unimplemented optimizations for lazy
   binding are to omit the lazy binding stub when linking with -z now
   and to move lazy binding stubs into a separate region for better
   cache behavior.  */

#define FDPIC_PLT_ENTRY_SIZE 28
#define FDPIC_PLT_LAZY_OFFSET 20

/* FIXME: The lazy binding stub requires a plt0 - which may need to be
   duplicated if it is out of range, or which can be inlined.  So
   right now it is always inlined, which wastes a word per stub.  It
   might be easier to handle the duplication if we put the lazy
   stubs separately.  */

static const bfd_byte fdpic_sh_plt_entry_be[FDPIC_PLT_ENTRY_SIZE] =
{
  0xd0, 0x02,	/* mov.l @(12,pc),r0 */
  0x01, 0xce,	/* mov.l @(r0,r12),r1 */
  0x70, 0x04,	/* add #4, r0 */
  0x41, 0x2b,	/* jmp @r1 */
  0x0c, 0xce,	/* mov.l @(r0,r12),r12 */
  0x00, 0x09,	/* nop */
  0, 0, 0, 0,	/* 0: replaced with offset of this symbol's funcdesc */
  0, 0, 0, 0,	/* 1: replaced with offset into relocation table.  */
  0x60, 0xc2,	/* mov.l @r12,r0 */
  0x40, 0x2b,	/* jmp @r0 */
  0x53, 0xc1,	/*  mov.l @(4,r12),r3 */
  0x00, 0x09,	/* nop */
};

static const bfd_byte fdpic_sh_plt_entry_le[FDPIC_PLT_ENTRY_SIZE] =
{
  0x02, 0xd0,	/* mov.l @(12,pc),r0 */
  0xce, 0x01,	/* mov.l @(r0,r12),r1 */
  0x04, 0x70,	/* add #4, r0 */
  0x2b, 0x41,	/* jmp @r1 */
  0xce, 0x0c,	/* mov.l @(r0,r12),r12 */
  0x09, 0x00,	/* nop */
  0, 0, 0, 0,	/* 0: replaced with offset of this symbol's funcdesc */
  0, 0, 0, 0,	/* 1: replaced with offset into relocation table.  */
  0xc2, 0x60,	/* mov.l @r12,r0 */
  0x2b, 0x40,	/* jmp @r0 */
  0xc1, 0x53,	/*  mov.l @(4,r12),r3 */
  0x09, 0x00,	/* nop */
};

static const struct elf_sh_plt_info fdpic_sh_plts[2] = {
  {
    /* Big-endian PIC.  */
    NULL,
    0,
    { MINUS_ONE, MINUS_ONE, MINUS_ONE },
    fdpic_sh_plt_entry_be,
    FDPIC_PLT_ENTRY_SIZE,
    { 12, MINUS_ONE, 16, FALSE },
    FDPIC_PLT_LAZY_OFFSET,
    NULL
  },
  {
    /* Little-endian PIC.  */
    NULL,
    0,
    { MINUS_ONE, MINUS_ONE, MINUS_ONE },
    fdpic_sh_plt_entry_le,
    FDPIC_PLT_ENTRY_SIZE,
    { 12, MINUS_ONE, 16, FALSE },
    FDPIC_PLT_LAZY_OFFSET,
    NULL
  },
};

/* On SH2A, we can use the movi20 instruction to generate shorter PLT
   entries for the first 64K slots.  We use the normal FDPIC PLT entry
   past that point; we could also use movi20s, which might be faster,
   but would not be any smaller.  */

#define FDPIC_SH2A_PLT_ENTRY_SIZE 24
#define FDPIC_SH2A_PLT_LAZY_OFFSET 16

static const bfd_byte fdpic_sh2a_plt_entry_be[FDPIC_SH2A_PLT_ENTRY_SIZE] =
{
  0, 0, 0, 0,	/* movi20 #gotofffuncdesc,r0 */
  0x01, 0xce,	/* mov.l @(r0,r12),r1 */
  0x70, 0x04,	/* add #4, r0 */
  0x41, 0x2b,	/* jmp @r1 */
  0x0c, 0xce,	/* mov.l @(r0,r12),r12 */
  0, 0, 0, 0,	/* 1: replaced with offset into relocation table.  */
  0x60, 0xc2,	/* mov.l @r12,r0 */
  0x40, 0x2b,	/* jmp @r0 */
  0x53, 0xc1,	/*  mov.l @(4,r12),r3 */
  0x00, 0x09,	/* nop */
};

static const bfd_byte fdpic_sh2a_plt_entry_le[FDPIC_SH2A_PLT_ENTRY_SIZE] =
{
  0, 0, 0, 0,	/* movi20 #gotofffuncdesc,r0 */
  0xce, 0x01,	/* mov.l @(r0,r12),r1 */
  0x04, 0x70,	/* add #4, r0 */
  0x2b, 0x41,	/* jmp @r1 */
  0xce, 0x0c,	/* mov.l @(r0,r12),r12 */
  0, 0, 0, 0,	/* 1: replaced with offset into relocation table.  */
  0xc2, 0x60,	/* mov.l @r12,r0 */
  0x2b, 0x40,	/* jmp @r0 */
  0xc1, 0x53,	/*  mov.l @(4,r12),r3 */
  0x09, 0x00,	/* nop */
};

static const struct elf_sh_plt_info fdpic_sh2a_short_plt_be = {
  /* Big-endian FDPIC, max index 64K.  */
  NULL,
  0,
  { MINUS_ONE, MINUS_ONE, MINUS_ONE },
  fdpic_sh2a_plt_entry_be,
  FDPIC_SH2A_PLT_ENTRY_SIZE,
  { 0, MINUS_ONE, 12, TRUE },
  FDPIC_SH2A_PLT_LAZY_OFFSET,
  NULL
};

static const struct elf_sh_plt_info fdpic_sh2a_short_plt_le = {
  /* Little-endian FDPIC, max index 64K.  */
  NULL,
  0,
  { MINUS_ONE, MINUS_ONE, MINUS_ONE },
  fdpic_sh2a_plt_entry_le,
  FDPIC_SH2A_PLT_ENTRY_SIZE,
  { 0, MINUS_ONE, 12, TRUE },
  FDPIC_SH2A_PLT_LAZY_OFFSET,
  NULL
};

static const struct elf_sh_plt_info fdpic_sh2a_plts[2] = {
  {
    /* Big-endian PIC.  */
    NULL,
    0,
    { MINUS_ONE, MINUS_ONE, MINUS_ONE },
    fdpic_sh_plt_entry_be,
    FDPIC_PLT_ENTRY_SIZE,
    { 12, MINUS_ONE, 16, FALSE },
    FDPIC_PLT_LAZY_OFFSET,
    &fdpic_sh2a_short_plt_be
  },
  {
    /* Little-endian PIC.  */
    NULL,
    0,
    { MINUS_ONE, MINUS_ONE, MINUS_ONE },
    fdpic_sh_plt_entry_le,
    FDPIC_PLT_ENTRY_SIZE,
    { 12, MINUS_ONE, 16, FALSE },
    FDPIC_PLT_LAZY_OFFSET,
    &fdpic_sh2a_short_plt_le
  },
};

/* Return the type of PLT associated with ABFD.  PIC_P is true if
   the object is position-independent.  */

static const struct elf_sh_plt_info *
get_plt_info (bfd *abfd, bfd_boolean pic_p)
{
  if (fdpic_object_p (abfd))
    {
      /* If any input file requires SH2A we can use a shorter PLT
	 sequence.  */
      if (sh_get_arch_from_bfd_mach (bfd_get_mach (abfd)) & arch_sh2a_base)
	return &fdpic_sh2a_plts[!bfd_big_endian (abfd)];
      else
	return &fdpic_sh_plts[!bfd_big_endian (abfd)];
    }
  if (vxworks_object_p (abfd))
    return &vxworks_sh_plts[pic_p][!bfd_big_endian (abfd)];
  return &elf_sh_plts[pic_p][!bfd_big_endian (abfd)];
}

/* Install a 32-bit PLT field starting at ADDR, which occurs in OUTPUT_BFD.
   VALUE is the field's value and CODE_P is true if VALUE refers to code,
   not data.  */

inline static void
install_plt_field (bfd *output_bfd, bfd_boolean code_p ATTRIBUTE_UNUSED,
		   unsigned long value, bfd_byte *addr)
{
  bfd_put_32 (output_bfd, value, addr);
}
#endif

/* The number of PLT entries which can use a shorter PLT, if any.
   Currently always 64K, since only SH-2A FDPIC uses this; a
   20-bit movi20 can address that many function descriptors below
   _GLOBAL_OFFSET_TABLE_.  */
#define MAX_SHORT_PLT 65536

/* Return the index of the PLT entry at byte offset OFFSET.  */

static bfd_vma
get_plt_index (const struct elf_sh_plt_info *info, bfd_vma offset)
{
  bfd_vma plt_index = 0;

  offset -= info->plt0_entry_size;
  if (info->short_plt != NULL)
    {
      if (offset > MAX_SHORT_PLT * info->short_plt->symbol_entry_size)
	{
	  plt_index = MAX_SHORT_PLT;
	  offset -= MAX_SHORT_PLT * info->short_plt->symbol_entry_size;
	}
      else
	info = info->short_plt;
    }
  return plt_index + offset / info->symbol_entry_size;
}

/* Do the inverse operation.  */

static bfd_vma
get_plt_offset (const struct elf_sh_plt_info *info, bfd_vma plt_index)
{
  bfd_vma offset = 0;

  if (info->short_plt != NULL)
    {
      if (plt_index > MAX_SHORT_PLT)
	{
	  offset = MAX_SHORT_PLT * info->short_plt->symbol_entry_size;
	  plt_index -= MAX_SHORT_PLT;
	}
      else
	info = info->short_plt;
    }
  return (offset + info->plt0_entry_size
	  + (plt_index * info->symbol_entry_size));
}

/* The sh linker needs to keep track of the number of relocs that it
   decides to copy as dynamic relocs in check_relocs for each symbol.
   This is so that it can later discard them if they are found to be
   unnecessary.  We store the information in a field extending the
   regular ELF linker hash table.  */

struct elf_sh_dyn_relocs
{
  struct elf_sh_dyn_relocs *next;

  /* The input section of the reloc.  */
  asection *sec;

  /* Total number of relocs copied for the input section.  */
  bfd_size_type count;

  /* Number of pc-relative relocs copied for the input section.  */
  bfd_size_type pc_count;
};

union gotref
{
  bfd_signed_vma refcount;
  bfd_vma offset;
};

/* sh ELF linker hash entry.  */

struct elf_sh_link_hash_entry
{
  struct elf_link_hash_entry root;

#ifdef INCLUDE_SHMEDIA
  union
  {
    bfd_signed_vma refcount;
    bfd_vma offset;
  } datalabel_got;
#endif

  /* Track dynamic relocs copied for this symbol.  */
  struct elf_sh_dyn_relocs *dyn_relocs;

  bfd_signed_vma gotplt_refcount;

  /* A local function descriptor, for FDPIC.  The refcount counts
     R_SH_FUNCDESC, R_SH_GOTOFFFUNCDESC, and R_SH_GOTOFFFUNCDESC20
     relocations; the PLT and GOT entry are accounted
     for separately.  After adjust_dynamic_symbol, the offset is
     MINUS_ONE if there is no local descriptor (dynamic linker
     managed and no PLT entry, or undefined weak non-dynamic).
     During check_relocs we do not yet know whether the local
     descriptor will be canonical.  */
  union gotref funcdesc;

  /* How many of the above refcounted relocations were R_SH_FUNCDESC,
     and thus require fixups or relocations.  */
  bfd_signed_vma abs_funcdesc_refcount;

  enum got_type {
    GOT_UNKNOWN = 0, GOT_NORMAL, GOT_TLS_GD, GOT_TLS_IE, GOT_FUNCDESC
  } got_type;
};

#define sh_elf_hash_entry(ent) ((struct elf_sh_link_hash_entry *)(ent))

struct sh_elf_obj_tdata
{
  struct elf_obj_tdata root;

  /* got_type for each local got entry.  */
  char *local_got_type;

  /* Function descriptor refcount and offset for each local symbol.  */
  union gotref *local_funcdesc;
};

#define sh_elf_tdata(abfd) \
  ((struct sh_elf_obj_tdata *) (abfd)->tdata.any)

#define sh_elf_local_got_type(abfd) \
  (sh_elf_tdata (abfd)->local_got_type)

#define sh_elf_local_funcdesc(abfd) \
  (sh_elf_tdata (abfd)->local_funcdesc)

#define is_sh_elf(bfd) \
  (bfd_get_flavour (bfd) == bfd_target_elf_flavour \
   && elf_tdata (bfd) != NULL \
   && elf_object_id (bfd) == SH_ELF_DATA)

/* Override the generic function because we need to store sh_elf_obj_tdata
   as the specific tdata.  */

static bfd_boolean
sh_elf_mkobject (bfd *abfd)
{
  return bfd_elf_allocate_object (abfd, sizeof (struct sh_elf_obj_tdata),
				  SH_ELF_DATA);
}

/* sh ELF linker hash table.  */

struct elf_sh_link_hash_table
{
  struct elf_link_hash_table root;

  /* Short-cuts to get to dynamic linker sections.  */
  asection *sdynbss;
  asection *srelbss;
  asection *sfuncdesc;
  asection *srelfuncdesc;
  asection *srofixup;

  /* The (unloaded but important) VxWorks .rela.plt.unloaded section.  */
  asection *srelplt2;

  /* Small local sym cache.  */
  struct sym_cache sym_cache;

  /* A counter or offset to track a TLS got entry.  */
  union
    {
      bfd_signed_vma refcount;
      bfd_vma offset;
    } tls_ldm_got;

  /* The type of PLT to use.  */
  const struct elf_sh_plt_info *plt_info;

  /* True if the target system is VxWorks.  */
  bfd_boolean vxworks_p;

  /* True if the target system uses FDPIC.  */
  bfd_boolean fdpic_p;
};

/* Traverse an sh ELF linker hash table.  */

#define sh_elf_link_hash_traverse(table, func, info)			\
  (elf_link_hash_traverse						\
   (&(table)->root,							\
    (bfd_boolean (*) (struct elf_link_hash_entry *, void *)) (func), \
    (info)))

/* Get the sh ELF linker hash table from a link_info structure.  */

#define sh_elf_hash_table(p) \
  (elf_hash_table_id ((struct elf_link_hash_table *) ((p)->hash)) \
  == SH_ELF_DATA ? ((struct elf_sh_link_hash_table *) ((p)->hash)) : NULL)

/* Create an entry in an sh ELF linker hash table.  */

static struct bfd_hash_entry *
sh_elf_link_hash_newfunc (struct bfd_hash_entry *entry,
			  struct bfd_hash_table *table,
			  const char *string)
{
  struct elf_sh_link_hash_entry *ret =
    (struct elf_sh_link_hash_entry *) entry;

  /* Allocate the structure if it has not already been allocated by a
     subclass.  */
  if (ret == (struct elf_sh_link_hash_entry *) NULL)
    ret = ((struct elf_sh_link_hash_entry *)
	   bfd_hash_allocate (table,
			      sizeof (struct elf_sh_link_hash_entry)));
  if (ret == (struct elf_sh_link_hash_entry *) NULL)
    return (struct bfd_hash_entry *) ret;

  /* Call the allocation method of the superclass.  */
  ret = ((struct elf_sh_link_hash_entry *)
	 _bfd_elf_link_hash_newfunc ((struct bfd_hash_entry *) ret,
				     table, string));
  if (ret != (struct elf_sh_link_hash_entry *) NULL)
    {
      ret->dyn_relocs = NULL;
      ret->gotplt_refcount = 0;
#ifdef INCLUDE_SHMEDIA
      ret->datalabel_got.refcount = ret->root.got.refcount;
#endif
      ret->funcdesc.refcount = 0;
      ret->abs_funcdesc_refcount = 0;
      ret->got_type = GOT_UNKNOWN;
    }

  return (struct bfd_hash_entry *) ret;
}

/* Create an sh ELF linker hash table.  */

static struct bfd_link_hash_table *
sh_elf_link_hash_table_create (bfd *abfd)
{
  struct elf_sh_link_hash_table *ret;
  bfd_size_type amt = sizeof (struct elf_sh_link_hash_table);

  ret = (struct elf_sh_link_hash_table *) bfd_zmalloc (amt);
  if (ret == (struct elf_sh_link_hash_table *) NULL)
    return NULL;

  if (!_bfd_elf_link_hash_table_init (&ret->root, abfd,
				      sh_elf_link_hash_newfunc,
				      sizeof (struct elf_sh_link_hash_entry),
				      SH_ELF_DATA))
    {
      free (ret);
      return NULL;
    }

  ret->vxworks_p = vxworks_object_p (abfd);
  ret->fdpic_p = fdpic_object_p (abfd);

  return &ret->root.root;
}

static bfd_boolean
sh_elf_omit_section_dynsym (bfd *output_bfd ATTRIBUTE_UNUSED,
			    struct bfd_link_info *info, asection *p)
{
  struct elf_sh_link_hash_table *htab = sh_elf_hash_table (info);

  /* Non-FDPIC binaries do not need dynamic symbols for sections.  */
  if (!htab->fdpic_p)
    return TRUE;

  /* We need dynamic symbols for every section, since segments can
     relocate independently.  */
  switch (elf_section_data (p)->this_hdr.sh_type)
    {
    case SHT_PROGBITS:
    case SHT_NOBITS:
      /* If sh_type is yet undecided, assume it could be
	 SHT_PROGBITS/SHT_NOBITS.  */
    case SHT_NULL:
      return FALSE;

      /* There shouldn't be section relative relocations
	 against any other section.  */
    default:
      return TRUE;
    }
}

/* Create .got, .gotplt, and .rela.got sections in DYNOBJ, and set up
   shortcuts to them in our hash table.  */

static bfd_boolean
create_got_section (bfd *dynobj, struct bfd_link_info *info)
{
  struct elf_sh_link_hash_table *htab;

  if (! _bfd_elf_create_got_section (dynobj, info))
    return FALSE;

  htab = sh_elf_hash_table (info);
  if (htab == NULL)
    return FALSE;

  htab->sfuncdesc = bfd_make_section_anyway_with_flags (dynobj, ".got.funcdesc",
							(SEC_ALLOC | SEC_LOAD
							 | SEC_HAS_CONTENTS
							 | SEC_IN_MEMORY
							 | SEC_LINKER_CREATED));
  if (htab->sfuncdesc == NULL
      || ! bfd_set_section_alignment (dynobj, htab->sfuncdesc, 2))
    return FALSE;

  htab->srelfuncdesc = bfd_make_section_anyway_with_flags (dynobj,
							   ".rela.got.funcdesc",
							   (SEC_ALLOC | SEC_LOAD
							    | SEC_HAS_CONTENTS
							    | SEC_IN_MEMORY
							    | SEC_LINKER_CREATED
							    | SEC_READONLY));
  if (htab->srelfuncdesc == NULL
      || ! bfd_set_section_alignment (dynobj, htab->srelfuncdesc, 2))
    return FALSE;

  /* Also create .rofixup.  */
  htab->srofixup = bfd_make_section_anyway_with_flags (dynobj, ".rofixup",
						       (SEC_ALLOC | SEC_LOAD
							| SEC_HAS_CONTENTS
							| SEC_IN_MEMORY
							| SEC_LINKER_CREATED
							| SEC_READONLY));
  if (htab->srofixup == NULL
      || ! bfd_set_section_alignment (dynobj, htab->srofixup, 2))
    return FALSE;

  return TRUE;
}

/* Create dynamic sections when linking against a dynamic object.  */

static bfd_boolean
sh_elf_create_dynamic_sections (bfd *abfd, struct bfd_link_info *info)
{
  struct elf_sh_link_hash_table *htab;
  flagword flags, pltflags;
  asection *s;
  const struct elf_backend_data *bed = get_elf_backend_data (abfd);
  int ptralign = 0;

  switch (bed->s->arch_size)
    {
    case 32:
      ptralign = 2;
      break;

    case 64:
      ptralign = 3;
      break;

    default:
      bfd_set_error (bfd_error_bad_value);
      return FALSE;
    }

  htab = sh_elf_hash_table (info);
  if (htab == NULL)
    return FALSE;

  if (htab->root.dynamic_sections_created)
    return TRUE;

  /* We need to create .plt, .rel[a].plt, .got, .got.plt, .dynbss, and
     .rel[a].bss sections.  */

  flags = (SEC_ALLOC | SEC_LOAD | SEC_HAS_CONTENTS | SEC_IN_MEMORY
	   | SEC_LINKER_CREATED);

  pltflags = flags;
  pltflags |= SEC_CODE;
  if (bed->plt_not_loaded)
    pltflags &= ~ (SEC_LOAD | SEC_HAS_CONTENTS);
  if (bed->plt_readonly)
    pltflags |= SEC_READONLY;

  s = bfd_make_section_anyway_with_flags (abfd, ".plt", pltflags);
  htab->root.splt = s;
  if (s == NULL
      || ! bfd_set_section_alignment (abfd, s, bed->plt_alignment))
    return FALSE;

  if (bed->want_plt_sym)
    {
      /* Define the symbol _PROCEDURE_LINKAGE_TABLE_ at the start of the
	 .plt section.  */
      struct elf_link_hash_entry *h;
      struct bfd_link_hash_entry *bh = NULL;

      if (! (_bfd_generic_link_add_one_symbol
	     (info, abfd, "_PROCEDURE_LINKAGE_TABLE_", BSF_GLOBAL, s,
	      (bfd_vma) 0, (const char *) NULL, FALSE,
	      get_elf_backend_data (abfd)->collect, &bh)))
	return FALSE;

      h = (struct elf_link_hash_entry *) bh;
      h->def_regular = 1;
      h->type = STT_OBJECT;
      htab->root.hplt = h;

      if (bfd_link_pic (info)
	  && ! bfd_elf_link_record_dynamic_symbol (info, h))
	return FALSE;
    }

  s = bfd_make_section_anyway_with_flags (abfd,
					  bed->default_use_rela_p
					  ? ".rela.plt" : ".rel.plt",
					  flags | SEC_READONLY);
  htab->root.srelplt = s;
  if (s == NULL
      || ! bfd_set_section_alignment (abfd, s, ptralign))
    return FALSE;

  if (htab->root.sgot == NULL
      && !create_got_section (abfd, info))
    return FALSE;

  if (bed->want_dynbss)
    {
      /* The .dynbss section is a place to put symbols which are defined
	 by dynamic objects, are referenced by regular objects, and are
	 not functions.  We must allocate space for them in the process
	 image and use a R_*_COPY reloc to tell the dynamic linker to
	 initialize them at run time.  The linker script puts the .dynbss
	 section into the .bss section of the final image.  */
      s = bfd_make_section_anyway_with_flags (abfd, ".dynbss",
					      SEC_ALLOC | SEC_LINKER_CREATED);
      htab->sdynbss = s;
      if (s == NULL)
	return FALSE;

      /* The .rel[a].bss section holds copy relocs.  This section is not
	 normally needed.  We need to create it here, though, so that the
	 linker will map it to an output section.  We can't just create it
	 only if we need it, because we will not know whether we need it
	 until we have seen all the input files, and the first time the
	 main linker code calls BFD after examining all the input files
	 (size_dynamic_sections) the input sections have already been
	 mapped to the output sections.  If the section turns out not to
	 be needed, we can discard it later.  We will never need this
	 section when generating a shared object, since they do not use
	 copy relocs.  */
      if (! bfd_link_pic (info))
	{
	  s = bfd_make_section_anyway_with_flags (abfd,
						  (bed->default_use_rela_p
						   ? ".rela.bss" : ".rel.bss"),
						  flags | SEC_READONLY);
	  htab->srelbss = s;
	  if (s == NULL
	      || ! bfd_set_section_alignment (abfd, s, ptralign))
	    return FALSE;
	}
    }

  if (htab->vxworks_p)
    {
      if (!elf_vxworks_create_dynamic_sections (abfd, info, &htab->srelplt2))
	return FALSE;
    }

  return TRUE;
}

/* Adjust a symbol defined by a dynamic object and referenced by a
   regular object.  The current definition is in some section of the
   dynamic object, but we're not including those sections.  We have to
   change the definition to something the rest of the link can
   understand.  */

static bfd_boolean
sh_elf_adjust_dynamic_symbol (struct bfd_link_info *info,
			      struct elf_link_hash_entry *h)
{
  struct elf_sh_link_hash_table *htab;
  struct elf_sh_link_hash_entry *eh;
  struct elf_sh_dyn_relocs *p;
  asection *s;

  htab = sh_elf_hash_table (info);
  if (htab == NULL)
    return FALSE;

  /* Make sure we know what is going on here.  */
  BFD_ASSERT (htab->root.dynobj != NULL
	      && (h->needs_plt
		  || h->is_weakalias
		  || (h->def_dynamic
		      && h->ref_regular
		      && !h->def_regular)));

  /* If this is a function, put it in the procedure linkage table.  We
     will fill in the contents of the procedure linkage table later,
     when we know the address of the .got section.  */
  if (h->type == STT_FUNC
      || h->needs_plt)
    {
      if (h->plt.refcount <= 0
	  || SYMBOL_CALLS_LOCAL (info, h)
	  || (ELF_ST_VISIBILITY (h->other) != STV_DEFAULT
	      && h->root.type == bfd_link_hash_undefweak))
	{
	  /* This case can occur if we saw a PLT reloc in an input
	     file, but the symbol was never referred to by a dynamic
	     object.  In such a case, we don't actually need to build
	     a procedure linkage table, and we can just do a REL32
	     reloc instead.  */
	  h->plt.offset = (bfd_vma) -1;
	  h->needs_plt = 0;
	}

      return TRUE;
    }
  else
    h->plt.offset = (bfd_vma) -1;

  /* If this is a weak symbol, and there is a real definition, the
     processor independent code will have arranged for us to see the
     real definition first, and we can just use the same value.  */
  if (h->is_weakalias)
    {
      struct elf_link_hash_entry *def = weakdef (h);
      BFD_ASSERT (def->root.type == bfd_link_hash_defined);
      h->root.u.def.section = def->root.u.def.section;
      h->root.u.def.value = def->root.u.def.value;
      if (info->nocopyreloc)
	h->non_got_ref = def->non_got_ref;
      return TRUE;
    }

  /* This is a reference to a symbol defined by a dynamic object which
     is not a function.  */

  /* If we are creating a shared library, we must presume that the
     only references to the symbol are via the global offset table.
     For such cases we need not do anything here; the relocations will
     be handled correctly by relocate_section.  */
  if (bfd_link_pic (info))
    return TRUE;

  /* If there are no references to this symbol that do not use the
     GOT, we don't need to generate a copy reloc.  */
  if (!h->non_got_ref)
    return TRUE;

  /* If -z nocopyreloc was given, we won't generate them either.  */
  if (info->nocopyreloc)
    {
      h->non_got_ref = 0;
      return TRUE;
    }

  eh = (struct elf_sh_link_hash_entry *) h;
  for (p = eh->dyn_relocs; p != NULL; p = p->next)
    {
      s = p->sec->output_section;
      if (s != NULL && (s->flags & (SEC_READONLY | SEC_HAS_CONTENTS)) != 0)
	break;
    }

  /* If we didn't find any dynamic relocs in sections which needs the
     copy reloc, then we'll be keeping the dynamic relocs and avoiding
     the copy reloc.  */
  if (p == NULL)
    {
      h->non_got_ref = 0;
      return TRUE;
    }

  /* We must allocate the symbol in our .dynbss section, which will
     become part of the .bss section of the executable.  There will be
     an entry for this symbol in the .dynsym section.  The dynamic
     object will contain position independent code, so all references
     from the dynamic object to this symbol will go through the global
     offset table.  The dynamic linker will use the .dynsym entry to
     determine the address it must put in the global offset table, so
     both the dynamic object and the regular object will refer to the
     same memory location for the variable.  */

  s = htab->sdynbss;
  BFD_ASSERT (s != NULL);

  /* We must generate a R_SH_COPY reloc to tell the dynamic linker to
     copy the initial value out of the dynamic object and into the
     runtime process image.  We need to remember the offset into the
     .rela.bss section we are going to use.  */
  if ((h->root.u.def.section->flags & SEC_ALLOC) != 0 && h->size != 0)
    {
      asection *srel;

      srel = htab->srelbss;
      BFD_ASSERT (srel != NULL);
      srel->size += sizeof (Elf32_External_Rela);
      h->needs_copy = 1;
    }

  return _bfd_elf_adjust_dynamic_copy (info, h, s);
}

/* Allocate space in .plt, .got and associated reloc sections for
   dynamic relocs.  */

static bfd_boolean
allocate_dynrelocs (struct elf_link_hash_entry *h, void *inf)
{
  struct bfd_link_info *info;
  struct elf_sh_link_hash_table *htab;
  struct elf_sh_link_hash_entry *eh;
  struct elf_sh_dyn_relocs *p;

  if (h->root.type == bfd_link_hash_indirect)
    return TRUE;

  info = (struct bfd_link_info *) inf;
  htab = sh_elf_hash_table (info);
  if (htab == NULL)
    return FALSE;

  eh = (struct elf_sh_link_hash_entry *) h;
  if ((h->got.refcount > 0
       || h->forced_local)
      && eh->gotplt_refcount > 0)
    {
      /* The symbol has been forced local, or we have some direct got refs,
	 so treat all the gotplt refs as got refs. */
      h->got.refcount += eh->gotplt_refcount;
      if (h->plt.refcount >= eh->gotplt_refcount)
	h->plt.refcount -= eh->gotplt_refcount;
    }

  if (htab->root.dynamic_sections_created
      && h->plt.refcount > 0
      && (ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
	  || h->root.type != bfd_link_hash_undefweak))
    {
      /* Make sure this symbol is output as a dynamic symbol.
	 Undefined weak syms won't yet be marked as dynamic.  */
      if (h->dynindx == -1
	  && !h->forced_local)
	{
	  if (! bfd_elf_link_record_dynamic_symbol (info, h))
	    return FALSE;
	}

      if (bfd_link_pic (info)
	  || WILL_CALL_FINISH_DYNAMIC_SYMBOL (1, 0, h))
	{
	  asection *s = htab->root.splt;
	  const struct elf_sh_plt_info *plt_info;

	  /* If this is the first .plt entry, make room for the special
	     first entry.  */
	  if (s->size == 0)
	    s->size += htab->plt_info->plt0_entry_size;

	  h->plt.offset = s->size;

	  /* If this symbol is not defined in a regular file, and we are
	     not generating a shared library, then set the symbol to this
	     location in the .plt.  This is required to make function
	     pointers compare as equal between the normal executable and
	     the shared library.  Skip this for FDPIC, since the
	     function's address will be the address of the canonical
	     function descriptor.  */
	  if (!htab->fdpic_p && !bfd_link_pic (info) && !h->def_regular)
	    {
	      h->root.u.def.section = s;
	      h->root.u.def.value = h->plt.offset;
	    }

	  /* Make room for this entry.  */
	  plt_info = htab->plt_info;
	  if (plt_info->short_plt != NULL
	      && (get_plt_index (plt_info->short_plt, s->size) < MAX_SHORT_PLT))
	    plt_info = plt_info->short_plt;
	  s->size += plt_info->symbol_entry_size;

	  /* We also need to make an entry in the .got.plt section, which
	     will be placed in the .got section by the linker script.  */
	  if (!htab->fdpic_p)
	    htab->root.sgotplt->size += 4;
	  else
	    htab->root.sgotplt->size += 8;

	  /* We also need to make an entry in the .rel.plt section.  */
	  htab->root.srelplt->size += sizeof (Elf32_External_Rela);

	  if (htab->vxworks_p && !bfd_link_pic (info))
	    {
	      /* VxWorks executables have a second set of relocations
		 for each PLT entry.  They go in a separate relocation
		 section, which is processed by the kernel loader.  */

	      /* There is a relocation for the initial PLT entry:
		 an R_SH_DIR32 relocation for _GLOBAL_OFFSET_TABLE_.  */
	      if (h->plt.offset == htab->plt_info->plt0_entry_size)
		htab->srelplt2->size += sizeof (Elf32_External_Rela);

	      /* There are two extra relocations for each subsequent
		 PLT entry: an R_SH_DIR32 relocation for the GOT entry,
		 and an R_SH_DIR32 relocation for the PLT entry.  */
	      htab->srelplt2->size += sizeof (Elf32_External_Rela) * 2;
	    }
	}
      else
	{
	  h->plt.offset = (bfd_vma) -1;
	  h->needs_plt = 0;
	}
    }
  else
    {
      h->plt.offset = (bfd_vma) -1;
      h->needs_plt = 0;
    }

  if (h->got.refcount > 0)
    {
      asection *s;
      bfd_boolean dyn;
      enum got_type got_type = sh_elf_hash_entry (h)->got_type;

      /* Make sure this symbol is output as a dynamic symbol.
	 Undefined weak syms won't yet be marked as dynamic.  */
      if (h->dynindx == -1
	  && !h->forced_local)
	{
	  if (! bfd_elf_link_record_dynamic_symbol (info, h))
	    return FALSE;
	}

      s = htab->root.sgot;
      h->got.offset = s->size;
      s->size += 4;
      /* R_SH_TLS_GD needs 2 consecutive GOT slots.  */
      if (got_type == GOT_TLS_GD)
	s->size += 4;
      dyn = htab->root.dynamic_sections_created;
      if (!dyn)
	{
	  /* No dynamic relocations required.  */
	  if (htab->fdpic_p && !bfd_link_pic (info)
	      && h->root.type != bfd_link_hash_undefweak
	      && (got_type == GOT_NORMAL || got_type == GOT_FUNCDESC))
	    htab->srofixup->size += 4;
	}
      /* No dynamic relocations required when IE->LE conversion happens.  */
      else if (got_type == GOT_TLS_IE
	       && !h->def_dynamic
	       && !bfd_link_pic (info))
	;
      /* R_SH_TLS_IE_32 needs one dynamic relocation if dynamic,
	 R_SH_TLS_GD needs one if local symbol and two if global.  */
      else if ((got_type == GOT_TLS_GD && h->dynindx == -1)
	       || got_type == GOT_TLS_IE)
	htab->root.srelgot->size += sizeof (Elf32_External_Rela);
      else if (got_type == GOT_TLS_GD)
	htab->root.srelgot->size += 2 * sizeof (Elf32_External_Rela);
      else if (got_type == GOT_FUNCDESC)
	{
	  if (!bfd_link_pic (info) && SYMBOL_FUNCDESC_LOCAL (info, h))
	    htab->srofixup->size += 4;
	  else
	    htab->root.srelgot->size += sizeof (Elf32_External_Rela);
	}
      else if ((ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
		|| h->root.type != bfd_link_hash_undefweak)
	       && (bfd_link_pic (info)
		   || WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, 0, h)))
	htab->root.srelgot->size += sizeof (Elf32_External_Rela);
      else if (htab->fdpic_p
	       && !bfd_link_pic (info)
	       && got_type == GOT_NORMAL
	       && (ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
		   || h->root.type != bfd_link_hash_undefweak))
	htab->srofixup->size += 4;
    }
  else
    h->got.offset = (bfd_vma) -1;

#ifdef INCLUDE_SHMEDIA
  if (eh->datalabel_got.refcount > 0)
    {
      asection *s;
      bfd_boolean dyn;

      /* Make sure this symbol is output as a dynamic symbol.
	 Undefined weak syms won't yet be marked as dynamic.  */
      if (h->dynindx == -1
	  && !h->forced_local)
	{
	  if (! bfd_elf_link_record_dynamic_symbol (info, h))
	    return FALSE;
	}

      s = htab->root.sgot;
      eh->datalabel_got.offset = s->size;
      s->size += 4;
      dyn = htab->root.dynamic_sections_created;
      if (WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn, bfd_link_pic (info), h))
	htab->root.srelgot->size += sizeof (Elf32_External_Rela);
    }
  else
    eh->datalabel_got.offset = (bfd_vma) -1;
#endif

  /* Allocate space for any dynamic relocations to function
     descriptors, canonical or otherwise.  We need to relocate the
     reference unless it resolves to zero, which only happens for
     undefined weak symbols (either non-default visibility, or when
     static linking).  Any GOT slot is accounted for elsewhere.  */
  if (eh->abs_funcdesc_refcount > 0
      && (h->root.type != bfd_link_hash_undefweak
	  || (htab->root.dynamic_sections_created
	      && ! SYMBOL_CALLS_LOCAL (info, h))))
    {
      if (!bfd_link_pic (info) && SYMBOL_FUNCDESC_LOCAL (info, h))
	htab->srofixup->size += eh->abs_funcdesc_refcount * 4;
      else
	htab->root.srelgot->size
	  += eh->abs_funcdesc_refcount * sizeof (Elf32_External_Rela);
    }

  /* We must allocate a function descriptor if there are references to
     a canonical descriptor (R_SH_GOTFUNCDESC or R_SH_FUNCDESC) and
     the dynamic linker isn't going to allocate it.  None of this
     applies if we already created one in .got.plt, but if the
     canonical function descriptor can be in this object, there
     won't be a PLT entry at all.  */
  if ((eh->funcdesc.refcount > 0
       || (h->got.offset != MINUS_ONE && eh->got_type == GOT_FUNCDESC))
      && h->root.type != bfd_link_hash_undefweak
      && SYMBOL_FUNCDESC_LOCAL (info, h))
    {
      /* Make room for this function descriptor.  */
      eh->funcdesc.offset = htab->sfuncdesc->size;
      htab->sfuncdesc->size += 8;

      /* We will need a relocation or two fixups to initialize the
	 function descriptor, so allocate those too.  */
      if (!bfd_link_pic (info) && SYMBOL_CALLS_LOCAL (info, h))
	htab->srofixup->size += 8;
      else
	htab->srelfuncdesc->size += sizeof (Elf32_External_Rela);
    }

  if (eh->dyn_relocs == NULL)
    return TRUE;

  /* In the shared -Bsymbolic case, discard space allocated for
     dynamic pc-relative relocs against symbols which turn out to be
     defined in regular objects.  For the normal shared case, discard
     space for pc-relative relocs that have become local due to symbol
     visibility changes.  */

  if (bfd_link_pic (info))
    {
      if (SYMBOL_CALLS_LOCAL (info, h))
	{
	  struct elf_sh_dyn_relocs **pp;

	  for (pp = &eh->dyn_relocs; (p = *pp) != NULL; )
	    {
	      p->count -= p->pc_count;
	      p->pc_count = 0;
	      if (p->count == 0)
		*pp = p->next;
	      else
		pp = &p->next;
	    }
	}

      if (htab->vxworks_p)
	{
	  struct elf_sh_dyn_relocs **pp;

	  for (pp = &eh->dyn_relocs; (p = *pp) != NULL; )
	    {
	      if (strcmp (p->sec->output_section->name, ".tls_vars") == 0)
		*pp = p->next;
	      else
		pp = &p->next;
	    }
	}

      /* Also discard relocs on undefined weak syms with non-default
	 visibility.  */
      if (eh->dyn_relocs != NULL
	  && h->root.type == bfd_link_hash_undefweak)
	{
	  if (ELF_ST_VISIBILITY (h->other) != STV_DEFAULT
	      || UNDEFWEAK_NO_DYNAMIC_RELOC (info, h))
	    eh->dyn_relocs = NULL;

	  /* Make sure undefined weak symbols are output as a dynamic
	     symbol in PIEs.  */
	  else if (h->dynindx == -1
		   && !h->forced_local)
	    {
	      if (! bfd_elf_link_record_dynamic_symbol (info, h))
		return FALSE;
	    }
	}
    }
  else
    {
      /* For the non-shared case, discard space for relocs against
	 symbols which turn out to need copy relocs or are not
	 dynamic.  */

      if (!h->non_got_ref
	  && ((h->def_dynamic
	       && !h->def_regular)
	      || (htab->root.dynamic_sections_created
		  && (h->root.type == bfd_link_hash_undefweak
		      || h->root.type == bfd_link_hash_undefined))))
	{
	  /* Make sure this symbol is output as a dynamic symbol.
	     Undefined weak syms won't yet be marked as dynamic.  */
	  if (h->dynindx == -1
	      && !h->forced_local)
	    {
	      if (! bfd_elf_link_record_dynamic_symbol (info, h))
		return FALSE;
	    }

	  /* If that succeeded, we know we'll be keeping all the
	     relocs.  */
	  if (h->dynindx != -1)
	    goto keep;
	}

      eh->dyn_relocs = NULL;

    keep: ;
    }

  /* Finally, allocate space.  */
  for (p = eh->dyn_relocs; p != NULL; p = p->next)
    {
      asection *sreloc = elf_section_data (p->sec)->sreloc;
      sreloc->size += p->count * sizeof (Elf32_External_Rela);

      /* If we need relocations, we do not need fixups.  */
      if (htab->fdpic_p && !bfd_link_pic (info))
	htab->srofixup->size -= 4 * (p->count - p->pc_count);
    }

  return TRUE;
}

/* Find any dynamic relocs that apply to read-only sections.  */

static bfd_boolean
readonly_dynrelocs (struct elf_link_hash_entry *h, void *inf)
{
  struct elf_sh_link_hash_entry *eh;
  struct elf_sh_dyn_relocs *p;

  eh = (struct elf_sh_link_hash_entry *) h;
  for (p = eh->dyn_relocs; p != NULL; p = p->next)
    {
      asection *s = p->sec->output_section;

      if (s != NULL && (s->flags & SEC_READONLY) != 0)
	{
	  struct bfd_link_info *info = (struct bfd_link_info *) inf;

	  info->flags |= DF_TEXTREL;

	  info->callbacks->minfo (_("%B: dynamic relocation in read-only section `%A'\n"),
				  p->sec->owner, p->sec);

	  /* Not an error, just cut short the traversal.  */
	  return FALSE;
	}
    }
  return TRUE;
}

/* This function is called after all the input files have been read,
   and the input sections have been assigned to output sections.
   It's a convenient place to determine the PLT style.  */

static bfd_boolean
sh_elf_always_size_sections (bfd *output_bfd, struct bfd_link_info *info)
{
  sh_elf_hash_table (info)->plt_info = get_plt_info (output_bfd,
						     bfd_link_pic (info));

  if (sh_elf_hash_table (info)->fdpic_p && !bfd_link_relocatable (info)
      && !bfd_elf_stack_segment_size (output_bfd, info,
				      "__stacksize", DEFAULT_STACK_SIZE))
    return FALSE;
  return TRUE;
}

/* Set the sizes of the dynamic sections.  */

static bfd_boolean
sh_elf_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
			      struct bfd_link_info *info)
{
  struct elf_sh_link_hash_table *htab;
  bfd *dynobj;
  asection *s;
  bfd_boolean relocs;
  bfd *ibfd;

  htab = sh_elf_hash_table (info);
  if (htab == NULL)
    return FALSE;

  dynobj = htab->root.dynobj;
  BFD_ASSERT (dynobj != NULL);

  if (htab->root.dynamic_sections_created)
    {
      /* Set the contents of the .interp section to the interpreter.  */
      if (bfd_link_executable (info) && !info->nointerp)
	{
	  s = bfd_get_linker_section (dynobj, ".interp");
	  BFD_ASSERT (s != NULL);
	  s->size = sizeof ELF_DYNAMIC_INTERPRETER;
	  s->contents = (unsigned char *) ELF_DYNAMIC_INTERPRETER;
	}
    }

  /* Set up .got offsets for local syms, and space for local dynamic
     relocs.  */
  for (ibfd = info->input_bfds; ibfd != NULL; ibfd = ibfd->link.next)
    {
      bfd_signed_vma *local_got;
      bfd_signed_vma *end_local_got;
      union gotref *local_funcdesc, *end_local_funcdesc;
      char *local_got_type;
      bfd_size_type locsymcount;
      Elf_Internal_Shdr *symtab_hdr;
      asection *srel;

      if (! is_sh_elf (ibfd))
	continue;

      for (s = ibfd->sections; s != NULL; s = s->next)
	{
	  struct elf_sh_dyn_relocs *p;

	  for (p = ((struct elf_sh_dyn_relocs *)
		    elf_section_data (s)->local_dynrel);
	       p != NULL;
	       p = p->next)
	    {
	      if (! bfd_is_abs_section (p->sec)
		  && bfd_is_abs_section (p->sec->output_section))
		{
		  /* Input section has been discarded, either because
		     it is a copy of a linkonce section or due to
		     linker script /DISCARD/, so we'll be discarding
		     the relocs too.  */
		}
	      else if (htab->vxworks_p
		       && strcmp (p->sec->output_section->name,
				  ".tls_vars") == 0)
		{
		  /* Relocations in vxworks .tls_vars sections are
		     handled specially by the loader.  */
		}
	      else if (p->count != 0)
		{
		  srel = elf_section_data (p->sec)->sreloc;
		  srel->size += p->count * sizeof (Elf32_External_Rela);
		  if ((p->sec->output_section->flags & SEC_READONLY) != 0)
		    {
		      info->flags |= DF_TEXTREL;
		      info->callbacks->minfo (_("%B: dynamic relocation in read-only section `%A'\n"),
					      p->sec->owner, p->sec);
		    }

		  /* If we need relocations, we do not need fixups.  */
		  if (htab->fdpic_p && !bfd_link_pic (info))
		    htab->srofixup->size -= 4 * (p->count - p->pc_count);
		}
	    }
	}

      symtab_hdr = &elf_symtab_hdr (ibfd);
      locsymcount = symtab_hdr->sh_info;
#ifdef INCLUDE_SHMEDIA
      /* Count datalabel local GOT.  */
      locsymcount *= 2;
#endif
      s = htab->root.sgot;
      srel = htab->root.srelgot;

      local_got = elf_local_got_refcounts (ibfd);
      if (local_got)
	{
	  end_local_got = local_got + locsymcount;
	  local_got_type = sh_elf_local_got_type (ibfd);
	  local_funcdesc = sh_elf_local_funcdesc (ibfd);
	  for (; local_got < end_local_got; ++local_got)
	    {
	      if (*local_got > 0)
		{
		  *local_got = s->size;
		  s->size += 4;
		  if (*local_got_type == GOT_TLS_GD)
		    s->size += 4;
		  if (bfd_link_pic (info))
		    srel->size += sizeof (Elf32_External_Rela);
		  else
		    htab->srofixup->size += 4;

		  if (*local_got_type == GOT_FUNCDESC)
		    {
		      if (local_funcdesc == NULL)
			{
			  bfd_size_type size;

			  size = locsymcount * sizeof (union gotref);
			  local_funcdesc = (union gotref *) bfd_zalloc (ibfd,
									size);
			  if (local_funcdesc == NULL)
			    return FALSE;
			  sh_elf_local_funcdesc (ibfd) = local_funcdesc;
			  local_funcdesc += (local_got
					     - elf_local_got_refcounts (ibfd));
			}
		      local_funcdesc->refcount++;
		      ++local_funcdesc;
		    }
		}
	      else
		*local_got = (bfd_vma) -1;
	      ++local_got_type;
	    }
	}

      local_funcdesc = sh_elf_local_funcdesc (ibfd);
      if (local_funcdesc)
	{
	  end_local_funcdesc = local_funcdesc + locsymcount;

	  for (; local_funcdesc < end_local_funcdesc; ++local_funcdesc)
	    {
	      if (local_funcdesc->refcount > 0)
		{
		  local_funcdesc->offset = htab->sfuncdesc->size;
		  htab->sfuncdesc->size += 8;
		  if (!bfd_link_pic (info))
		    htab->srofixup->size += 8;
		  else
		    htab->srelfuncdesc->size += sizeof (Elf32_External_Rela);
		}
	      else
		local_funcdesc->offset = MINUS_ONE;
	    }
	}

    }

  if (htab->tls_ldm_got.refcount > 0)
    {
      /* Allocate 2 got entries and 1 dynamic reloc for R_SH_TLS_LD_32
	 relocs.  */
      htab->tls_ldm_got.offset = htab->root.sgot->size;
      htab->root.sgot->size += 8;
      htab->root.srelgot->size += sizeof (Elf32_External_Rela);
    }
  else
    htab->tls_ldm_got.offset = -1;

  /* Only the reserved entries should be present.  For FDPIC, they go at
     the end of .got.plt.  */
  if (htab->fdpic_p)
    {
      BFD_ASSERT (htab->root.sgotplt && htab->root.sgotplt->size == 12);
      htab->root.sgotplt->size = 0;
    }

  /* Allocate global sym .plt and .got entries, and space for global
     sym dynamic relocs.  */
  elf_link_hash_traverse (&htab->root, allocate_dynrelocs, info);

  /* Move the reserved entries and the _GLOBAL_OFFSET_TABLE_ symbol to the
     end of the FDPIC .got.plt.  */
  if (htab->fdpic_p)
    {
      htab->root.hgot->root.u.def.value = htab->root.sgotplt->size;
      htab->root.sgotplt->size += 12;
    }

  /* At the very end of the .rofixup section is a pointer to the GOT.  */
  if (htab->fdpic_p && htab->srofixup != NULL)
    htab->srofixup->size += 4;

  /* We now have determined the sizes of the various dynamic sections.
     Allocate memory for them.  */
  relocs = FALSE;
  for (s = dynobj->sections; s != NULL; s = s->next)
    {
      if ((s->flags & SEC_LINKER_CREATED) == 0)
	continue;

      if (s == htab->root.splt
	  || s == htab->root.sgot
	  || s == htab->root.sgotplt
	  || s == htab->sfuncdesc
	  || s == htab->srofixup
	  || s == htab->sdynbss)
	{
	  /* Strip this section if we don't need it; see the
	     comment below.  */
	}
      else if (CONST_STRNEQ (bfd_get_section_name (dynobj, s), ".rela"))
	{
	  if (s->size != 0 && s != htab->root.srelplt && s != htab->srelplt2)
	    relocs = TRUE;

	  /* We use the reloc_count field as a counter if we need
	     to copy relocs into the output file.  */
	  s->reloc_count = 0;
	}
      else
	{
	  /* It's not one of our sections, so don't allocate space.  */
	  continue;
	}

      if (s->size == 0)
	{
	  /* If we don't need this section, strip it from the
	     output file.  This is mostly to handle .rela.bss and
	     .rela.plt.  We must create both sections in
	     create_dynamic_sections, because they must be created
	     before the linker maps input sections to output
	     sections.  The linker does that before
	     adjust_dynamic_symbol is called, and it is that
	     function which decides whether anything needs to go
	     into these sections.  */

	  s->flags |= SEC_EXCLUDE;
	  continue;
	}

      if ((s->flags & SEC_HAS_CONTENTS) == 0)
	continue;

      /* Allocate memory for the section contents.  We use bfd_zalloc
	 here in case unused entries are not reclaimed before the
	 section's contents are written out.  This should not happen,
	 but this way if it does, we get a R_SH_NONE reloc instead
	 of garbage.  */
      s->contents = (bfd_byte *) bfd_zalloc (dynobj, s->size);
      if (s->contents == NULL)
	return FALSE;
    }

  if (htab->root.dynamic_sections_created)
    {
      /* Add some entries to the .dynamic section.  We fill in the
	 values later, in sh_elf_finish_dynamic_sections, but we
	 must add the entries now so that we get the correct size for
	 the .dynamic section.  The DT_DEBUG entry is filled in by the
	 dynamic linker and used by the debugger.  */
#define add_dynamic_entry(TAG, VAL) \
  _bfd_elf_add_dynamic_entry (info, TAG, VAL)

      if (bfd_link_executable (info))
	{
	  if (! add_dynamic_entry (DT_DEBUG, 0))
	    return FALSE;
	}

      if (htab->root.splt->size != 0)
	{
	  if (! add_dynamic_entry (DT_PLTGOT, 0)
	      || ! add_dynamic_entry (DT_PLTRELSZ, 0)
	      || ! add_dynamic_entry (DT_PLTREL, DT_RELA)
	      || ! add_dynamic_entry (DT_JMPREL, 0))
	    return FALSE;
	}
      else if ((elf_elfheader (output_bfd)->e_flags & EF_SH_FDPIC))
	{
	  if (! add_dynamic_entry (DT_PLTGOT, 0))
	    return FALSE;
	}

      if (relocs)
	{
	  if (! add_dynamic_entry (DT_RELA, 0)
	      || ! add_dynamic_entry (DT_RELASZ, 0)
	      || ! add_dynamic_entry (DT_RELAENT,
				      sizeof (Elf32_External_Rela)))
	    return FALSE;

	  /* If any dynamic relocs apply to a read-only section,
	     then we need a DT_TEXTREL entry.  */
	  if ((info->flags & DF_TEXTREL) == 0)
	    elf_link_hash_traverse (&htab->root, readonly_dynrelocs, info);

	  if ((info->flags & DF_TEXTREL) != 0)
	    {
	      if (! add_dynamic_entry (DT_TEXTREL, 0))
		return FALSE;
	    }
	}
      if (htab->vxworks_p
	  && !elf_vxworks_add_dynamic_entries (output_bfd, info))
	return FALSE;
    }
#undef add_dynamic_entry

  return TRUE;
}

/* Add a dynamic relocation to the SRELOC section.  */

inline static bfd_vma
sh_elf_add_dyn_reloc (bfd *output_bfd, asection *sreloc, bfd_vma offset,
		      int reloc_type, long dynindx, bfd_vma addend)
{
  Elf_Internal_Rela outrel;
  bfd_vma reloc_offset;

  outrel.r_offset = offset;
  outrel.r_info = ELF32_R_INFO (dynindx, reloc_type);
  outrel.r_addend = addend;

  reloc_offset = sreloc->reloc_count * sizeof (Elf32_External_Rela);
  BFD_ASSERT (reloc_offset < sreloc->size);
  bfd_elf32_swap_reloca_out (output_bfd, &outrel,
			     sreloc->contents + reloc_offset);
  sreloc->reloc_count++;

  return reloc_offset;
}

/* Add an FDPIC read-only fixup.  */

inline static void
sh_elf_add_rofixup (bfd *output_bfd, asection *srofixup, bfd_vma offset)
{
  bfd_vma fixup_offset;

  fixup_offset = srofixup->reloc_count++ * 4;
  BFD_ASSERT (fixup_offset < srofixup->size);
  bfd_put_32 (output_bfd, offset, srofixup->contents + fixup_offset);
}

/* Return the offset of the generated .got section from the
   _GLOBAL_OFFSET_TABLE_ symbol.  */

static bfd_signed_vma
sh_elf_got_offset (struct elf_sh_link_hash_table *htab)
{
  return (htab->root.sgot->output_offset - htab->root.sgotplt->output_offset
	  - htab->root.hgot->root.u.def.value);
}

/* Find the segment number in which OSEC, and output section, is
   located.  */

static unsigned
sh_elf_osec_to_segment (bfd *output_bfd, asection *osec)
{
  Elf_Internal_Phdr *p = NULL;

  if (output_bfd->xvec->flavour == bfd_target_elf_flavour
      /* PR ld/17110: Do not look for output segments in an input bfd.  */
      && output_bfd->direction != read_direction)
    p = _bfd_elf_find_segment_containing_section (output_bfd, osec);

  /* FIXME: Nothing ever says what this index is relative to.  The kernel
     supplies data in terms of the number of load segments but this is
     a phdr index and the first phdr may not be a load segment.  */
  return (p != NULL) ? p - elf_tdata (output_bfd)->phdr : -1;
}

static bfd_boolean
sh_elf_osec_readonly_p (bfd *output_bfd, asection *osec)
{
  unsigned seg = sh_elf_osec_to_segment (output_bfd, osec);

  return (seg != (unsigned) -1
	  && ! (elf_tdata (output_bfd)->phdr[seg].p_flags & PF_W));
}

/* Generate the initial contents of a local function descriptor, along
   with any relocations or fixups required.  */
static bfd_boolean
sh_elf_initialize_funcdesc (bfd *output_bfd,
			    struct bfd_link_info *info,
			    struct elf_link_hash_entry *h,
			    bfd_vma offset,
			    asection *section,
			    bfd_vma value)
{
  struct elf_sh_link_hash_table *htab;
  int dynindx;
  bfd_vma addr, seg;

  htab = sh_elf_hash_table (info);

  /* FIXME: The ABI says that the offset to the function goes in the
     descriptor, along with the segment index.  We're RELA, so it could
     go in the reloc instead... */

  if (h != NULL && SYMBOL_CALLS_LOCAL (info, h))
    {
      section = h->root.u.def.section;
      value = h->root.u.def.value;
    }

  if (h == NULL || SYMBOL_CALLS_LOCAL (info, h))
    {
      dynindx = elf_section_data (section->output_section)->dynindx;
      addr = value + section->output_offset;
      seg = sh_elf_osec_to_segment (output_bfd, section->output_section);
    }
  else
    {
      BFD_ASSERT (h->dynindx != -1);
      dynindx = h->dynindx;
      addr = seg = 0;
    }

  if (!bfd_link_pic (info) && SYMBOL_CALLS_LOCAL (info, h))
    {
      if (h == NULL || h->root.type != bfd_link_hash_undefweak)
	{
	  sh_elf_add_rofixup (output_bfd, htab->srofixup,
			      offset
			      + htab->sfuncdesc->output_section->vma
			      + htab->sfuncdesc->output_offset);
	  sh_elf_add_rofixup (output_bfd, htab->srofixup,
			      offset + 4
			      + htab->sfuncdesc->output_section->vma
			      + htab->sfuncdesc->output_offset);
	}

      /* There are no dynamic relocations so fill in the final
	 address and gp value (barring fixups).  */
      addr += section->output_section->vma;
      seg = htab->root.hgot->root.u.def.value
	+ htab->root.hgot->root.u.def.section->output_section->vma
	+ htab->root.hgot->root.u.def.section->output_offset;
    }
  else
    sh_elf_add_dyn_reloc (output_bfd, htab->srelfuncdesc,
			  offset
			  + htab->sfuncdesc->output_section->vma
			  + htab->sfuncdesc->output_offset,
			  R_SH_FUNCDESC_VALUE, dynindx, 0);

  bfd_put_32 (output_bfd, addr, htab->sfuncdesc->contents + offset);
  bfd_put_32 (output_bfd, seg, htab->sfuncdesc->contents + offset + 4);

  return TRUE;
}

/* Install a 20-bit movi20 field starting at ADDR, which occurs in OUTPUT_BFD.
   VALUE is the field's value.  Return bfd_reloc_ok if successful or an error
   otherwise.  */

static bfd_reloc_status_type
install_movi20_field (bfd *output_bfd, unsigned long relocation,
		      bfd *input_bfd, asection *input_section,
		      bfd_byte *contents, bfd_vma offset)
{
  unsigned long cur_val;
  bfd_byte *addr;
  bfd_reloc_status_type r;

  if (offset > bfd_get_section_limit (input_bfd, input_section))
    return bfd_reloc_outofrange;

  r = bfd_check_overflow (complain_overflow_signed, 20, 0,
			  bfd_arch_bits_per_address (input_bfd), relocation);
  if (r != bfd_reloc_ok)
    return r;

  addr = contents + offset;
  cur_val = bfd_get_16 (output_bfd, addr);
  bfd_put_16 (output_bfd, cur_val | ((relocation & 0xf0000) >> 12), addr);
  bfd_put_16 (output_bfd, relocation & 0xffff, addr + 2);

  return bfd_reloc_ok;
}

/* Relocate an SH ELF section.  */

static bfd_boolean
sh_elf_relocate_section (bfd *output_bfd, struct bfd_link_info *info,
			 bfd *input_bfd, asection *input_section,
			 bfd_byte *contents, Elf_Internal_Rela *relocs,
			 Elf_Internal_Sym *local_syms,
			 asection **local_sections)
{
  struct elf_sh_link_hash_table *htab;
  Elf_Internal_Shdr *symtab_hdr;
  struct elf_link_hash_entry **sym_hashes;
  Elf_Internal_Rela *rel, *relend;
  bfd_vma *local_got_offsets;
  asection *sgot = NULL;
  asection *sgotplt = NULL;
  asection *splt = NULL;
  asection *sreloc = NULL;
  asection *srelgot = NULL;
  bfd_boolean is_vxworks_tls;
  unsigned isec_segment, got_segment, plt_segment, check_segment[2];
  bfd_boolean fdpic_p = FALSE;

  BFD_ASSERT (is_sh_elf (input_bfd));

  htab = sh_elf_hash_table (info);
  if (htab != NULL)
    {
      sgot = htab->root.sgot;
      sgotplt = htab->root.sgotplt;
      srelgot = htab->root.srelgot;
      splt = htab->root.splt;
      fdpic_p = htab->fdpic_p;
    }
  symtab_hdr = &elf_symtab_hdr (input_bfd);
  sym_hashes = elf_sym_hashes (input_bfd);
  local_got_offsets = elf_local_got_offsets (input_bfd);

  isec_segment = sh_elf_osec_to_segment (output_bfd,
					 input_section->output_section);
  if (fdpic_p && sgot)
    got_segment = sh_elf_osec_to_segment (output_bfd,
					  sgot->output_section);
  else
    got_segment = -1;
  if (fdpic_p && splt)
    plt_segment = sh_elf_osec_to_segment (output_bfd,
					  splt->output_section);
  else
    plt_segment = -1;

  /* We have to handle relocations in vxworks .tls_vars sections
     specially, because the dynamic loader is 'weird'.  */
  is_vxworks_tls = (htab && htab->vxworks_p && bfd_link_pic (info)
		    && !strcmp (input_section->output_section->name,
				".tls_vars"));

  rel = relocs;
  relend = relocs + input_section->reloc_count;
  for (; rel < relend; rel++)
    {
      int r_type;
      reloc_howto_type *howto;
      unsigned long r_symndx;
      Elf_Internal_Sym *sym;
      asection *sec;
      struct elf_link_hash_entry *h;
      bfd_vma relocation;
      bfd_vma addend = (bfd_vma) 0;
      bfd_reloc_status_type r;
      int seen_stt_datalabel = 0;
      bfd_vma off;
      enum got_type got_type;
      const char *symname = NULL;
      bfd_boolean resolved_to_zero;

      r_symndx = ELF32_R_SYM (rel->r_info);

      r_type = ELF32_R_TYPE (rel->r_info);

      /* Many of the relocs are only used for relaxing, and are
	 handled entirely by the relaxation code.  */
      if (r_type >= (int) R_SH_GNU_VTINHERIT
	  && r_type <= (int) R_SH_LABEL)
	continue;
      if (r_type == (int) R_SH_NONE)
	continue;

      if (r_type < 0
	  || r_type >= R_SH_max
	  || (r_type >= (int) R_SH_FIRST_INVALID_RELOC
	      && r_type <= (int) R_SH_LAST_INVALID_RELOC)
	  || (r_type >= (int) R_SH_FIRST_INVALID_RELOC_2
	      && r_type <= (int) R_SH_LAST_INVALID_RELOC_2)
	  || (   r_type >= (int) R_SH_FIRST_INVALID_RELOC_3
	      && r_type <= (int) R_SH_LAST_INVALID_RELOC_3)
	  || (   r_type >= (int) R_SH_FIRST_INVALID_RELOC_4
	      && r_type <= (int) R_SH_LAST_INVALID_RELOC_4)
	  || (   r_type >= (int) R_SH_FIRST_INVALID_RELOC_5
	      && r_type <= (int) R_SH_LAST_INVALID_RELOC_5)
	  || (   r_type >= (int) R_SH_FIRST_INVALID_RELOC_6
	      && r_type <= (int) R_SH_LAST_INVALID_RELOC_6))
	{
	  bfd_set_error (bfd_error_bad_value);
	  return FALSE;
	}

      howto = get_howto_table (output_bfd) + r_type;

      /* For relocs that aren't partial_inplace, we get the addend from
	 the relocation.  */
      if (! howto->partial_inplace)
	addend = rel->r_addend;

      resolved_to_zero = FALSE;
      h = NULL;
      sym = NULL;
      sec = NULL;
      check_segment[0] = -1;
      check_segment[1] = -1;
      if (r_symndx < symtab_hdr->sh_info)
	{
	  sym = local_syms + r_symndx;
	  sec = local_sections[r_symndx];

	  symname = bfd_elf_string_from_elf_section
	    (input_bfd, symtab_hdr->sh_link, sym->st_name);
	  if (symname == NULL || *symname == '\0')
	    symname = bfd_section_name (input_bfd, sec);

	  relocation = (sec->output_section->vma
			+ sec->output_offset
			+ sym->st_value);
	  /* A local symbol never has STO_SH5_ISA32, so we don't need
	     datalabel processing here.  Make sure this does not change
	     without notice.  */
	  if ((sym->st_other & STO_SH5_ISA32) != 0)
	    (*info->callbacks->reloc_dangerous)
	      (info,
	       _("Unexpected STO_SH5_ISA32 on local symbol is not handled"),
	       input_bfd, input_section, rel->r_offset);

	  if (sec != NULL && discarded_section (sec))
	    /* Handled below.  */
	    ;
	  else if (bfd_link_relocatable (info))
	    {
	      /* This is a relocatable link.  We don't have to change
		 anything, unless the reloc is against a section symbol,
		 in which case we have to adjust according to where the
		 section symbol winds up in the output section.  */
	      if (ELF_ST_TYPE (sym->st_info) == STT_SECTION)
		{
		  if (! howto->partial_inplace)
		    {
		      /* For relocations with the addend in the
			 relocation, we need just to update the addend.
			 All real relocs are of type partial_inplace; this
			 code is mostly for completeness.  */
		      rel->r_addend += sec->output_offset;

		      continue;
		    }

		  /* Relocs of type partial_inplace need to pick up the
		     contents in the contents and add the offset resulting
		     from the changed location of the section symbol.
		     Using _bfd_final_link_relocate (e.g. goto
		     final_link_relocate) here would be wrong, because
		     relocations marked pc_relative would get the current
		     location subtracted, and we must only do that at the
		     final link.  */
		  r = _bfd_relocate_contents (howto, input_bfd,
					      sec->output_offset
					      + sym->st_value,
					      contents + rel->r_offset);
		  goto relocation_done;
		}

	      continue;
	    }
	  else if (! howto->partial_inplace)
	    {
	      relocation = _bfd_elf_rela_local_sym (output_bfd, sym, &sec, rel);
	      addend = rel->r_addend;
	    }
	  else if ((sec->flags & SEC_MERGE)
		   && ELF_ST_TYPE (sym->st_info) == STT_SECTION)
	    {
	      asection *msec;

	      if (howto->rightshift || howto->src_mask != 0xffffffff)
		{
		  _bfd_error_handler
		    /* xgettext:c-format */
		    (_("%B(%A+%#Lx): %s relocation against SEC_MERGE section"),
		     input_bfd, input_section,
		     rel->r_offset, howto->name);
		  return FALSE;
		}

	      addend = bfd_get_32 (input_bfd, contents + rel->r_offset);
	      msec = sec;
	      addend =
		_bfd_elf_rel_local_sym (output_bfd, sym, &msec, addend)
		- relocation;
	      addend += msec->output_section->vma + msec->output_offset;
	      bfd_put_32 (input_bfd, addend, contents + rel->r_offset);
	      addend = 0;
	    }
	}
      else
	{
	  /* FIXME: Ought to make use of the RELOC_FOR_GLOBAL_SYMBOL macro.  */

	  relocation = 0;
	  h = sym_hashes[r_symndx - symtab_hdr->sh_info];
	  symname = h->root.root.string;
	  while (h->root.type == bfd_link_hash_indirect
		 || h->root.type == bfd_link_hash_warning)
	    {
#ifdef INCLUDE_SHMEDIA
	      /* If the reference passes a symbol marked with
		 STT_DATALABEL, then any STO_SH5_ISA32 on the final value
		 doesn't count.  */
	      seen_stt_datalabel |= h->type == STT_DATALABEL;
#endif
	      h = (struct elf_link_hash_entry *) h->root.u.i.link;
	    }
	  if (h->root.type == bfd_link_hash_defined
	      || h->root.type == bfd_link_hash_defweak)
	    {
	      bfd_boolean dyn;

	      dyn = htab ? htab->root.dynamic_sections_created : FALSE;
	      sec = h->root.u.def.section;
	      /* In these cases, we don't need the relocation value.
		 We check specially because in some obscure cases
		 sec->output_section will be NULL.  */
	      if (r_type == R_SH_GOTPC
		  || r_type == R_SH_GOTPC_LOW16
		  || r_type == R_SH_GOTPC_MEDLOW16
		  || r_type == R_SH_GOTPC_MEDHI16
		  || r_type == R_SH_GOTPC_HI16
		  || ((r_type == R_SH_PLT32
		       || r_type == R_SH_PLT_LOW16
		       || r_type == R_SH_PLT_MEDLOW16
		       || r_type == R_SH_PLT_MEDHI16
		       || r_type == R_SH_PLT_HI16)
		      && h->plt.offset != (bfd_vma) -1)
		  || ((r_type == R_SH_GOT32
		       || r_type == R_SH_GOT20
		       || r_type == R_SH_GOTFUNCDESC
		       || r_type == R_SH_GOTFUNCDESC20
		       || r_type == R_SH_GOTOFFFUNCDESC
		       || r_type == R_SH_GOTOFFFUNCDESC20
		       || r_type == R_SH_FUNCDESC
		       || r_type == R_SH_GOT_LOW16
		       || r_type == R_SH_GOT_MEDLOW16
		       || r_type == R_SH_GOT_MEDHI16
		       || r_type == R_SH_GOT_HI16)
		      && WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn,
							  bfd_link_pic (info),
							  h)
		      && (! bfd_link_pic (info)
			  || (! info->symbolic && h->dynindx != -1)
			  || !h->def_regular))
		  /* The cases above are those in which relocation is
		     overwritten in the switch block below.  The cases
		     below are those in which we must defer relocation
		     to run-time, because we can't resolve absolute
		     addresses when creating a shared library.  */
		  || (bfd_link_pic (info)
		      && ((! info->symbolic && h->dynindx != -1)
			  || !h->def_regular)
		      && ((r_type == R_SH_DIR32
			   && !h->forced_local)
			  || (r_type == R_SH_REL32
			      && !SYMBOL_CALLS_LOCAL (info, h)))
		      && ((input_section->flags & SEC_ALLOC) != 0
			  /* DWARF will emit R_SH_DIR32 relocations in its
			     sections against symbols defined externally
			     in shared libraries.  We can't do anything
			     with them here.  */
			  || ((input_section->flags & SEC_DEBUGGING) != 0
			      && h->def_dynamic)))
		  /* Dynamic relocs are not propagated for SEC_DEBUGGING
		     sections because such sections are not SEC_ALLOC and
		     thus ld.so will not process them.  */
		  || (sec->output_section == NULL
		      && ((input_section->flags & SEC_DEBUGGING) != 0
			  && h->def_dynamic))
		  || (sec->output_section == NULL
		      && (sh_elf_hash_entry (h)->got_type == GOT_TLS_IE
			  || sh_elf_hash_entry (h)->got_type == GOT_TLS_GD)))
		;
	      else if (sec->output_section != NULL)
		relocation = ((h->root.u.def.value
			      + sec->output_section->vma
			      + sec->output_offset)
			      /* A STO_SH5_ISA32 causes a "bitor 1" to the
				 symbol value, unless we've seen
				 STT_DATALABEL on the way to it.  */
			      | ((h->other & STO_SH5_ISA32) != 0
				 && ! seen_stt_datalabel));
	      else if (!bfd_link_relocatable (info)
		       && (_bfd_elf_section_offset (output_bfd, info,
						    input_section,
						    rel->r_offset)
			   != (bfd_vma) -1))
		{
		  _bfd_error_handler
		    /* xgettext:c-format */
		    (_("%B(%A+%#Lx): unresolvable %s relocation against symbol `%s'"),
		     input_bfd,
		     input_section,
		     rel->r_offset,
		     howto->name,
		     h->root.root.string);
		  return FALSE;
		}
	    }
	  else if (h->root.type == bfd_link_hash_undefweak)
	    resolved_to_zero = UNDEFWEAK_NO_DYNAMIC_RELOC (info, h);
	  else if (info->unresolved_syms_in_objects == RM_IGNORE
		   && ELF_ST_VISIBILITY (h->other) == STV_DEFAULT)
	    ;
	  else if (!bfd_link_relocatable (info))
	    (*info->callbacks->undefined_symbol)
	      (info, h->root.root.string, input_bfd,
	       input_section, rel->r_offset,
	       (info->unresolved_syms_in_objects == RM_GENERATE_ERROR
		|| ELF_ST_VISIBILITY (h->other)));
	}

      if (sec != NULL && discarded_section (sec))
	RELOC_AGAINST_DISCARDED_SECTION (info, input_bfd, input_section,
					 rel, 1, relend, howto, 0, contents);

      if (bfd_link_relocatable (info))
	continue;

      /* Check for inter-segment relocations in FDPIC files.  Most
	 relocations connect the relocation site to the location of
	 the target symbol, but there are some exceptions below.  */
      check_segment[0] = isec_segment;
      if (sec != NULL)
	check_segment[1] = sh_elf_osec_to_segment (output_bfd,
						   sec->output_section);
      else
	check_segment[1] = -1;

      switch ((int) r_type)
	{
	final_link_relocate:
	  /* COFF relocs don't use the addend. The addend is used for
	     R_SH_DIR32 to be compatible with other compilers.  */
	  r = _bfd_final_link_relocate (howto, input_bfd, input_section,
					contents, rel->r_offset,
					relocation, addend);
	  break;

	case R_SH_IND12W:
	  goto final_link_relocate;

	case R_SH_DIR8WPN:
	case R_SH_DIR8WPZ:
	case R_SH_DIR8WPL:
	  /* If the reloc is against the start of this section, then
	     the assembler has already taken care of it and the reloc
	     is here only to assist in relaxing.  If the reloc is not
	     against the start of this section, then it's against an
	     external symbol and we must deal with it ourselves.  */
	  if (input_section->output_section->vma + input_section->output_offset
	      != relocation)
	    {
	      int disp = (relocation
			  - input_section->output_section->vma
			  - input_section->output_offset
			  - rel->r_offset);
	      int mask = 0;
	      switch (r_type)
		{
		case R_SH_DIR8WPN:
		case R_SH_DIR8WPZ: mask = 1; break;
		case R_SH_DIR8WPL: mask = 3; break;
		default: mask = 0; break;
		}
	      if (disp & mask)
		{
		  _bfd_error_handler
		    /* xgettext:c-format */
		    (_("%B: %#Lx: fatal: unaligned branch target for relax-support relocation"),
		     input_section->owner,
		     rel->r_offset);
		  bfd_set_error (bfd_error_bad_value);
		  return FALSE;
		}
	      relocation -= 4;
	      goto final_link_relocate;
	    }
	  r = bfd_reloc_ok;
	  break;

	default:
#ifdef INCLUDE_SHMEDIA
	  if (shmedia_prepare_reloc (info, input_bfd, input_section,
				     contents, rel, &relocation))
	    goto final_link_relocate;
#endif
	  bfd_set_error (bfd_error_bad_value);
	  return FALSE;

	case R_SH_DIR16:
	case R_SH_DIR8:
	case R_SH_DIR8U:
	case R_SH_DIR8S:
	case R_SH_DIR4U:
	  goto final_link_relocate;

	case R_SH_DIR8UL:
	case R_SH_DIR4UL:
	  if (relocation & 3)
	    {
	      _bfd_error_handler
		/* xgettext:c-format */
		(_("%B: %#Lx: fatal: unaligned %s relocation %#Lx"),
		 input_section->owner,
		 rel->r_offset, howto->name,
		 relocation);
	      bfd_set_error (bfd_error_bad_value);
	      return FALSE;
	    }
	  goto final_link_relocate;

	case R_SH_DIR8UW:
	case R_SH_DIR8SW:
	case R_SH_DIR4UW:
	  if (relocation & 1)
	    {
	      _bfd_error_handler
		/* xgettext:c-format */
		(_("%B: %#Lx: fatal: unaligned %s relocation %#Lx"),
		 input_section->owner,
		 rel->r_offset, howto->name,
		 relocation);
	      bfd_set_error (bfd_error_bad_value);
	      return FALSE;
	    }
	  goto final_link_relocate;

	case R_SH_PSHA:
	  if ((signed int)relocation < -32
	      || (signed int)relocation > 32)
	    {
	      _bfd_error_handler
		/* xgettext:c-format */
		(_("%B: %#Lx: fatal: R_SH_PSHA relocation %Ld not in range -32..32"),
		 input_section->owner,
		 rel->r_offset,
		 relocation);
	      bfd_set_error (bfd_error_bad_value);
	      return FALSE;
	    }
	  goto final_link_relocate;

	case R_SH_PSHL:
	  if ((signed int)relocation < -16
	      || (signed int)relocation > 16)
	    {
	      _bfd_error_handler
		/* xgettext:c-format */
		(_("%B: %#Lx: fatal: R_SH_PSHL relocation %Ld not in range -32..32"),
		 input_section->owner,
		 rel->r_offset,
		 relocation);
	      bfd_set_error (bfd_error_bad_value);
	      return FALSE;
	    }
	  goto final_link_relocate;

	case R_SH_DIR32:
	case R_SH_REL32:
#ifdef INCLUDE_SHMEDIA
	case R_SH_IMM_LOW16_PCREL:
	case R_SH_IMM_MEDLOW16_PCREL:
	case R_SH_IMM_MEDHI16_PCREL:
	case R_SH_IMM_HI16_PCREL:
#endif
	  if (bfd_link_pic (info)
	      && (h == NULL
		  || (ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
		      && !resolved_to_zero)
		  || h->root.type != bfd_link_hash_undefweak)
	      && r_symndx != STN_UNDEF
	      && (input_section->flags & SEC_ALLOC) != 0
	      && !is_vxworks_tls
	      && (r_type == R_SH_DIR32
		  || !SYMBOL_CALLS_LOCAL (info, h)))
	    {
	      Elf_Internal_Rela outrel;
	      bfd_byte *loc;
	      bfd_boolean skip, relocate;

	      /* When generating a shared object, these relocations
		 are copied into the output file to be resolved at run
		 time.  */

	      if (sreloc == NULL)
		{
		  sreloc = _bfd_elf_get_dynamic_reloc_section
		    (input_bfd, input_section, /*rela?*/ TRUE);
		  if (sreloc == NULL)
		    return FALSE;
		}

	      skip = FALSE;
	      relocate = FALSE;

	      outrel.r_offset =
		_bfd_elf_section_offset (output_bfd, info, input_section,
					 rel->r_offset);
	      if (outrel.r_offset == (bfd_vma) -1)
		skip = TRUE;
	      else if (outrel.r_offset == (bfd_vma) -2)
		skip = TRUE, relocate = TRUE;
	      outrel.r_offset += (input_section->output_section->vma
				  + input_section->output_offset);

	      if (skip)
		memset (&outrel, 0, sizeof outrel);
	      else if (r_type == R_SH_REL32)
		{
		  BFD_ASSERT (h != NULL && h->dynindx != -1);
		  outrel.r_info = ELF32_R_INFO (h->dynindx, R_SH_REL32);
		  outrel.r_addend
		    = (howto->partial_inplace
		       ? bfd_get_32 (input_bfd, contents + rel->r_offset)
		       : addend);
		}
#ifdef INCLUDE_SHMEDIA
	      else if (r_type == R_SH_IMM_LOW16_PCREL
		       || r_type == R_SH_IMM_MEDLOW16_PCREL
		       || r_type == R_SH_IMM_MEDHI16_PCREL
		       || r_type == R_SH_IMM_HI16_PCREL)
		{
		  BFD_ASSERT (h != NULL && h->dynindx != -1);
		  outrel.r_info = ELF32_R_INFO (h->dynindx, r_type);
		  outrel.r_addend = addend;
		}
#endif
	      else if (fdpic_p
		       && (h == NULL
			   || ((info->symbolic || h->dynindx == -1)
			       && h->def_regular)))
		{
		  int dynindx;

		  BFD_ASSERT (sec != NULL);
		  BFD_ASSERT (sec->output_section != NULL);
		  dynindx = elf_section_data (sec->output_section)->dynindx;
		  outrel.r_info = ELF32_R_INFO (dynindx, R_SH_DIR32);
		  outrel.r_addend = relocation;
		  outrel.r_addend
		    += (howto->partial_inplace
			? bfd_get_32 (input_bfd, contents + rel->r_offset)
			: addend);
		  outrel.r_addend -= sec->output_section->vma;
		}
	      else
		{
		  /* h->dynindx may be -1 if this symbol was marked to
		     become local.  */
		  if (h == NULL
		      || ((info->symbolic || h->dynindx == -1)
			  && h->def_regular))
		    {
		      relocate = howto->partial_inplace;
		      outrel.r_info = ELF32_R_INFO (0, R_SH_RELATIVE);
		    }
		  else
		    {
		      BFD_ASSERT (h->dynindx != -1);
		      outrel.r_info = ELF32_R_INFO (h->dynindx, R_SH_DIR32);
		    }
		  outrel.r_addend = relocation;
		  outrel.r_addend
		    += (howto->partial_inplace
			? bfd_get_32 (input_bfd, contents + rel->r_offset)
			: addend);
		}

	      loc = sreloc->contents;
	      loc += sreloc->reloc_count++ * sizeof (Elf32_External_Rela);
	      bfd_elf32_swap_reloca_out (output_bfd, &outrel, loc);

	      check_segment[0] = check_segment[1] = -1;

	      /* If this reloc is against an external symbol, we do
		 not want to fiddle with the addend.  Otherwise, we
		 need to include the symbol value so that it becomes
		 an addend for the dynamic reloc.  */
	      if (! relocate)
		continue;
	    }
	  else if (fdpic_p && !bfd_link_pic (info)
		   && r_type == R_SH_DIR32
		   && (input_section->flags & SEC_ALLOC) != 0)
	    {
	      bfd_vma offset;

	      BFD_ASSERT (htab);

		if (sh_elf_osec_readonly_p (output_bfd,
					    input_section->output_section))
		  {
		    _bfd_error_handler
		      /* xgettext:c-format */
		      (_("%B(%A+%#Lx): cannot emit fixup to `%s' in read-only section"),
		       input_bfd,
		       input_section,
		       rel->r_offset,
		       symname);
		    return FALSE;
		  }

	      offset = _bfd_elf_section_offset (output_bfd, info,
						input_section, rel->r_offset);
	      if (offset != (bfd_vma)-1)
		sh_elf_add_rofixup (output_bfd, htab->srofixup,
				    input_section->output_section->vma
				    + input_section->output_offset
				    + rel->r_offset);

	      check_segment[0] = check_segment[1] = -1;
	    }
	    /* We don't want warnings for non-NULL tests on undefined weak
	       symbols.  */
	    else if (r_type == R_SH_REL32
		     && h
		     && h->root.type == bfd_link_hash_undefweak)
	      check_segment[0] = check_segment[1] = -1;
	  goto final_link_relocate;

	case R_SH_GOTPLT32:
#ifdef INCLUDE_SHMEDIA
	case R_SH_GOTPLT_LOW16:
	case R_SH_GOTPLT_MEDLOW16:
	case R_SH_GOTPLT_MEDHI16:
	case R_SH_GOTPLT_HI16:
	case R_SH_GOTPLT10BY4:
	case R_SH_GOTPLT10BY8:
#endif
	  /* Relocation is to the entry for this symbol in the
	     procedure linkage table.  */

	  if (h == NULL
	      || h->forced_local
	      || ! bfd_link_pic (info)
	      || info->symbolic
	      || h->dynindx == -1
	      || h->plt.offset == (bfd_vma) -1
	      || h->got.offset != (bfd_vma) -1)
	    goto force_got;

	  /* Relocation is to the entry for this symbol in the global
	     offset table extension for the procedure linkage table.  */

	  BFD_ASSERT (htab);
	  BFD_ASSERT (sgotplt != NULL);
	  relocation = (sgotplt->output_offset
			+ (get_plt_index (htab->plt_info, h->plt.offset)
			   + 3) * 4);

#ifdef GOT_BIAS
	  relocation -= GOT_BIAS;
#endif

	  goto final_link_relocate;

	force_got:
	case R_SH_GOT32:
	case R_SH_GOT20:
#ifdef INCLUDE_SHMEDIA
	case R_SH_GOT_LOW16:
	case R_SH_GOT_MEDLOW16:
	case R_SH_GOT_MEDHI16:
	case R_SH_GOT_HI16:
	case R_SH_GOT10BY4:
	case R_SH_GOT10BY8:
#endif
	  /* Relocation is to the entry for this symbol in the global
	     offset table.  */

	  BFD_ASSERT (htab);
	  BFD_ASSERT (sgot != NULL);
	  check_segment[0] = check_segment[1] = -1;

	  if (h != NULL)
	    {
	      bfd_boolean dyn;

	      off = h->got.offset;
#ifdef INCLUDE_SHMEDIA
	      if (seen_stt_datalabel)
		{
		  struct elf_sh_link_hash_entry *hsh;

		  hsh = (struct elf_sh_link_hash_entry *)h;
		  off = hsh->datalabel_got.offset;
		}
#endif
	      BFD_ASSERT (off != (bfd_vma) -1);

	      dyn = htab->root.dynamic_sections_created;
	      if (! WILL_CALL_FINISH_DYNAMIC_SYMBOL (dyn,
						     bfd_link_pic (info),
						     h)
		  || (bfd_link_pic (info)
		      && SYMBOL_REFERENCES_LOCAL (info, h))
		  || ((ELF_ST_VISIBILITY (h->other)
		       || resolved_to_zero)
		      && h->root.type == bfd_link_hash_undefweak))
		{
		  /* This is actually a static link, or it is a
		     -Bsymbolic link and the symbol is defined
		     locally, or the symbol was forced to be local
		     because of a version file.  We must initialize
		     this entry in the global offset table.  Since the
		     offset must always be a multiple of 4, we use the
		     least significant bit to record whether we have
		     initialized it already.

		     When doing a dynamic link, we create a .rela.got
		     relocation entry to initialize the value.  This
		     is done in the finish_dynamic_symbol routine.  */
		  if ((off & 1) != 0)
		    off &= ~1;
		  else
		    {
		      bfd_put_32 (output_bfd, relocation,
				  sgot->contents + off);
#ifdef INCLUDE_SHMEDIA
		      if (seen_stt_datalabel)
			{
			  struct elf_sh_link_hash_entry *hsh;

			  hsh = (struct elf_sh_link_hash_entry *)h;
			  hsh->datalabel_got.offset |= 1;
			}
		      else
#endif
			h->got.offset |= 1;

		      /* If we initialize the GOT entry here with a valid
			 symbol address, also add a fixup.  */
		      if (fdpic_p && !bfd_link_pic (info)
			  && sh_elf_hash_entry (h)->got_type == GOT_NORMAL
			  && (ELF_ST_VISIBILITY (h->other) == STV_DEFAULT
			      || h->root.type != bfd_link_hash_undefweak))
			sh_elf_add_rofixup (output_bfd, htab->srofixup,
					    sgot->output_section->vma
					    + sgot->output_offset
					    + off);
		    }
		}

	      relocation = sh_elf_got_offset (htab) + off;
	    }
	  else
	    {
#ifdef INCLUDE_SHMEDIA
	      if (rel->r_addend)
		{
		  BFD_ASSERT (local_got_offsets != NULL
			      && (local_got_offsets[symtab_hdr->sh_info
						    + r_symndx]
				  != (bfd_vma) -1));

		  off = local_got_offsets[symtab_hdr->sh_info
					  + r_symndx];
		}
	      else
		{
#endif
	      BFD_ASSERT (local_got_offsets != NULL
			  && local_got_offsets[r_symndx] != (bfd_vma) -1);

	      off = local_got_offsets[r_symndx];
#ifdef INCLUDE_SHMEDIA
		}
#endif

	      /* The offset must always be a multiple of 4.  We use
		 the least significant bit to record whether we have
		 already generated the necessary reloc.  */
	      if ((off & 1) != 0)
		off &= ~1;
	      else
		{
		  bfd_put_32 (output_bfd, relocation, sgot->contents + off);

		  if (bfd_link_pic (info))
		    {
		      Elf_Internal_Rela outrel;
		      bfd_byte *loc;

		      outrel.r_offset = (sgot->output_section->vma
					 + sgot->output_offset
					 + off);
		      if (fdpic_p)
			{
			  int dynindx
			    = elf_section_data (sec->output_section)->dynindx;
			  outrel.r_info = ELF32_R_INFO (dynindx, R_SH_DIR32);
			  outrel.r_addend = relocation;
			  outrel.r_addend -= sec->output_section->vma;
			}
		      else
			{
			  outrel.r_info = ELF32_R_INFO (0, R_SH_RELATIVE);
			  outrel.r_addend = relocation;
			}
		      loc = srelgot->contents;
		      loc += srelgot->reloc_count++ * sizeof (Elf32_External_Rela);
		      bfd_elf32_swap_reloca_out (output_bfd, &outrel, loc);
		    }
		  else if (fdpic_p
			   && (sh_elf_local_got_type (input_bfd) [r_symndx]
			       == GOT_NORMAL))
		    sh_elf_add_rofixup (output_bfd, htab->srofixup,
					sgot->output_section->vma
					+ sgot->output_offset
					+ off);

#ifdef INCLUDE_SHMEDIA
		  if (rel->r_addend)
		    local_got_offsets[symtab_hdr->sh_info + r_symndx] |= 1;
		  else
#endif
		    local_got_offsets[r_symndx] |= 1;
		}

	      relocation = sh_elf_got_offset (htab) + off;
	    }

#ifdef GOT_BIAS
	  relocation -= GOT_BIAS;
#endif

	  if (r_type == R_SH_GOT20)
	    {
	      r = install_movi20_field (output_bfd, relocation + addend,
					input_bfd, input_section, contents,
					rel->r_offset);
	      break;
	    }
	  else
	    goto final_link_relocate;

	case R_SH_GOTOFF:
	case R_SH_GOTOFF20:
#ifdef INCLUDE_SHMEDIA
	case R_SH_GOTOFF_LOW16:
	case R_SH_GOTOFF_MEDLOW16:
	case R_SH_GOTOFF_MEDHI16:
	case R_SH_GOTOFF_HI16:
#endif
	  /* GOTOFF relocations are relative to _GLOBAL_OFFSET_TABLE_, which
	     we place at the start of the .got.plt section.  This is the same
	     as the start of the output .got section, unless there are function
	     descriptors in front of it.  */
	  BFD_ASSERT (htab);
	  BFD_ASSERT (sgotplt != NULL);
	  check_segment[0] = got_segment;
	  relocation -= sgotplt->output_section->vma + sgotplt->output_offset
	    + htab->root.hgot->root.u.def.value;

#ifdef GOT_BIAS
	  relocation -= GOT_BIAS;
#endif

	  addend = rel->r_addend;

	  if (r_type == R_SH_GOTOFF20)
	    {
	      r = install_movi20_field (output_bfd, relocation + addend,
					input_bfd, input_section, contents,
					rel->r_offset);
	      break;
	    }
	  else
	    goto final_link_relocate;

	case R_SH_GOTPC:
#ifdef INCLUDE_SHMEDIA
	case R_SH_GOTPC_LOW16:
	case R_SH_GOTPC_MEDLOW16:
	case R_SH_GOTPC_MEDHI16:
	case R_SH_GOTPC_HI16:
#endif
	  /* Use global offset table as symbol value.  */

	  BFD_ASSERT (sgotplt != NULL);
	  relocation = sgotplt->output_section->vma + sgotplt->output_offset;

#ifdef GOT_BIAS
	  relocation += GOT_BIAS;
#endif

	  addend = rel->r_addend;

	  goto final_link_relocate;

	case R_SH_PLT32:
#ifdef INCLUDE_SHMEDIA
	case R_SH_PLT_LOW16:
	case R_SH_PLT_MEDLOW16:
	case R_SH_PLT_MEDHI16:
	case R_SH_PLT_HI16:
#endif
	  /* Relocation is to the entry for this symbol in the
	     procedure linkage table.  */

	  /* Resolve a PLT reloc against a local symbol directly,
	     without using the procedure linkage table.  */
	  if (h == NULL)
	    goto final_link_relocate;

	  /* We don't want to warn on calls to undefined weak symbols,
	     as calls to them must be protected by non-NULL tests
	     anyway, and unprotected calls would invoke undefined
	     behavior.  */
	  if (h->root.type == bfd_link_hash_undefweak)
	    check_segment[0] = check_segment[1] = -1;

	  if (h->forced_local)
	    goto final_link_relocate;

	  if (h->plt.offset == (bfd_vma) -1)
	    {
	      /* We didn't make a PLT entry for this symbol.  This
		 happens when statically linking PIC code, or when
		 using -Bsymbolic.  */
	      goto final_link_relocate;
	    }

	  BFD_ASSERT (splt != NULL);
	  check_segment[1] = plt_segment;
	  relocation = (splt->output_section->vma
			+ splt->output_offset
			+ h->plt.offset);

#ifdef INCLUDE_SHMEDIA
	  relocation++;
#endif

	  addend = rel->r_addend;

	  goto final_link_relocate;

	/* Relocation is to the canonical function descriptor for this
	   symbol, possibly via the GOT.  Initialize the GOT
	   entry and function descriptor if necessary.  */
	case R_SH_GOTFUNCDESC:
	case R_SH_GOTFUNCDESC20:
	case R_SH_FUNCDESC:
	  {
	    int dynindx = -1;
	    asection *reloc_section;
	    bfd_vma reloc_offset;
	    int reloc_type = R_SH_FUNCDESC;

	    BFD_ASSERT (htab);

	    check_segment[0] = check_segment[1] = -1;

	    /* FIXME: See what FRV does for global symbols in the
	       executable, with --export-dynamic.  Do they need ld.so
	       to allocate official descriptors?  See what this code
	       does.  */

	    relocation = 0;
	    addend = 0;

	    if (r_type == R_SH_FUNCDESC)
	      {
		reloc_section = input_section;
		reloc_offset = rel->r_offset;
	      }
	    else
	      {
		reloc_section = sgot;

		if (h != NULL)
		  reloc_offset = h->got.offset;
		else
		  {
		    BFD_ASSERT (local_got_offsets != NULL);
		    reloc_offset = local_got_offsets[r_symndx];
		  }
		BFD_ASSERT (reloc_offset != MINUS_ONE);

		if (reloc_offset & 1)
		  {
		    reloc_offset &= ~1;
		    goto funcdesc_done_got;
		  }
	      }

	    if (h && h->root.type == bfd_link_hash_undefweak
		&& (SYMBOL_CALLS_LOCAL (info, h)
		    || !htab->root.dynamic_sections_created))
	      /* Undefined weak symbol which will not be dynamically
		 resolved later; leave it at zero.  */
	      goto funcdesc_leave_zero;
	    else if (SYMBOL_CALLS_LOCAL (info, h)
		     && ! SYMBOL_FUNCDESC_LOCAL (info, h))
	      {
		/* If the symbol needs a non-local function descriptor
		   but binds locally (i.e., its visibility is
		   protected), emit a dynamic relocation decayed to
		   section+offset.  This is an optimization; the dynamic
		   linker would resolve our function descriptor request
		   to our copy of the function anyway.  */
		dynindx = elf_section_data (h->root.u.def.section
					    ->output_section)->dynindx;
		relocation += h->root.u.def.section->output_offset
		  + h->root.u.def.value;
	      }
	    else if (! SYMBOL_FUNCDESC_LOCAL (info, h))
	      {
		/* If the symbol is dynamic and there will be dynamic
		   symbol resolution because we are or are linked with a
		   shared library, emit a FUNCDESC relocation such that
		   the dynamic linker will allocate the function
		   descriptor.  */
		BFD_ASSERT (h->dynindx != -1);
		dynindx = h->dynindx;
	      }
	    else
	      {
		bfd_vma offset;

		/* Otherwise, we know we have a private function
		   descriptor, so reference it directly.  */
		reloc_type = R_SH_DIR32;
		dynindx = elf_section_data (htab->sfuncdesc
					    ->output_section)->dynindx;

		if (h)
		  {
		    offset = sh_elf_hash_entry (h)->funcdesc.offset;
		    BFD_ASSERT (offset != MINUS_ONE);
		    if ((offset & 1) == 0)
		      {
			if (!sh_elf_initialize_funcdesc (output_bfd, info, h,
							 offset, NULL, 0))
			  return FALSE;
			sh_elf_hash_entry (h)->funcdesc.offset |= 1;
		      }
		  }
		else
		  {
		    union gotref *local_funcdesc;

		    local_funcdesc = sh_elf_local_funcdesc (input_bfd);
		    offset = local_funcdesc[r_symndx].offset;
		    BFD_ASSERT (offset != MINUS_ONE);
		    if ((offset & 1) == 0)
		      {
			if (!sh_elf_initialize_funcdesc (output_bfd, info, NULL,
							 offset, sec,
							 sym->st_value))
			  return FALSE;
			local_funcdesc[r_symndx].offset |= 1;
		      }
		  }

		relocation = htab->sfuncdesc->output_offset + (offset & ~1);
	      }

	    if (!bfd_link_pic (info) && SYMBOL_FUNCDESC_LOCAL (info, h))
	      {
		bfd_vma offset;

		if (sh_elf_osec_readonly_p (output_bfd,
					    reloc_section->output_section))
		  {
		    _bfd_error_handler
		      /* xgettext:c-format */
		      (_("%B(%A+%#Lx): cannot emit fixup to `%s' in read-only section"),
		       input_bfd,
		       input_section,
		       rel->r_offset,
		       symname);
		    return FALSE;
		  }

		offset = _bfd_elf_section_offset (output_bfd, info,
						  reloc_section, reloc_offset);

		if (offset != (bfd_vma)-1)
		  sh_elf_add_rofixup (output_bfd, htab->srofixup,
				      offset
				      + reloc_section->output_section->vma
				      + reloc_section->output_offset);
	      }
	    else if ((reloc_section->output_section->flags
		      & (SEC_ALLOC | SEC_LOAD)) == (SEC_ALLOC | SEC_LOAD))
	      {
		bfd_vma offset;

		if (sh_elf_osec_readonly_p (output_bfd,
					    reloc_section->output_section))
		  {
		    info->callbacks->warning
		      (info,
		       _("cannot emit dynamic relocations in read-only section"),
		       symname, input_bfd, reloc_section, reloc_offset);
		    return FALSE;
		  }

		offset = _bfd_elf_section_offset (output_bfd, info,
						  reloc_section, reloc_offset);

		if (offset != (bfd_vma)-1)
		  sh_elf_add_dyn_reloc (output_bfd, srelgot,
					offset
					+ reloc_section->output_section->vma
					+ reloc_section->output_offset,
					reloc_type, dynindx, relocation);

		if (r_type == R_SH_FUNCDESC)
		  {
		    r = bfd_reloc_ok;
		    break;
		  }
		else
		  {
		    relocation = 0;
		    goto funcdesc_leave_zero;
		  }
	      }

	    if (SYMBOL_FUNCDESC_LOCAL (info, h))
	      relocation += htab->sfuncdesc->output_section->vma;
	  funcdesc_leave_zero:
	    if (r_type != R_SH_FUNCDESC)
	      {
		bfd_put_32 (output_bfd, relocation,
			    reloc_section->contents + reloc_offset);
		if (h != NULL)
		  h->got.offset |= 1;
		else
		  local_got_offsets[r_symndx] |= 1;

	      funcdesc_done_got:

		relocation = sh_elf_got_offset (htab) + reloc_offset;
#ifdef GOT_BIAS
		relocation -= GOT_BIAS;
#endif
	      }
	    if (r_type == R_SH_GOTFUNCDESC20)
	      {
		r = install_movi20_field (output_bfd, relocation + addend,
					  input_bfd, input_section, contents,
					  rel->r_offset);
		break;
	      }
	    else
	      goto final_link_relocate;
	  }
	  break;

	case R_SH_GOTOFFFUNCDESC:
	case R_SH_GOTOFFFUNCDESC20:
	  /* FIXME: See R_SH_FUNCDESC comment about global symbols in the
	     executable and --export-dynamic.  If such symbols get
	     ld.so-allocated descriptors we can not use R_SH_GOTOFFFUNCDESC
	     for them.  */
	  BFD_ASSERT (htab);

	  check_segment[0] = check_segment[1] = -1;
	  relocation = 0;
	  addend = rel->r_addend;

	  if (h && (h->root.type == bfd_link_hash_undefweak
		    || !SYMBOL_FUNCDESC_LOCAL (info, h)))
	    {
	      _bfd_error_handler
		/* xgettext:c-format */
		(_("%B(%A+%#Lx): %s relocation against external symbol \"%s\""),
		 input_bfd, input_section, rel->r_offset, howto->name,
		 h->root.root.string);
	      return FALSE;
	    }
	  else
	    {
	      bfd_vma offset;

	      /* Otherwise, we know we have a private function
		 descriptor, so reference it directly.  */
	      if (h)
		{
		  offset = sh_elf_hash_entry (h)->funcdesc.offset;
		  BFD_ASSERT (offset != MINUS_ONE);
		  if ((offset & 1) == 0)
		    {
		      if (!sh_elf_initialize_funcdesc (output_bfd, info, h,
						       offset, NULL, 0))
			return FALSE;
		      sh_elf_hash_entry (h)->funcdesc.offset |= 1;
		    }
		}
	      else
		{
		  union gotref *local_funcdesc;

		  local_funcdesc = sh_elf_local_funcdesc (input_bfd);
		  offset = local_funcdesc[r_symndx].offset;
		  BFD_ASSERT (offset != MINUS_ONE);
		  if ((offset & 1) == 0)
		    {
		      if (!sh_elf_initialize_funcdesc (output_bfd, info, NULL,
						       offset, sec,
						       sym->st_value))
			return FALSE;
		      local_funcdesc[r_symndx].offset |= 1;
		    }
		}

	      relocation = htab->sfuncdesc->output_offset + (offset & ~1);
	    }

	  relocation -= (htab->root.hgot->root.u.def.value
			 + sgotplt->output_offset);
#ifdef GOT_BIAS
	  relocation -= GOT_BIAS;
#endif

	  if (r_type == R_SH_GOTOFFFUNCDESC20)
	    {
	      r = install_movi20_field (output_bfd, relocation + addend,
					input_bfd, input_section, contents,
					rel->r_offset);
	      break;
	    }
	  else
	    goto final_link_relocate;

	case R_SH_LOOP_START:
	  {
	    static bfd_vma start, end;

	    start = (relocation + rel->r_addend
		     - (sec->output_section->vma + sec->output_offset));
	    r = sh_elf_reloc_loop (r_type, input_bfd, input_section, contents,
				   rel->r_offset, sec, start, end);
	    break;

	case R_SH_LOOP_END:
	    end = (relocation + rel->r_addend
		   - (sec->output_section->vma + sec->output_offset));
	    r = sh_elf_reloc_loop (r_type, input_bfd, input_section, contents,
				   rel->r_offset, sec, start, end);
	    break;
	  }

	case R_SH_TLS_GD_32:
	case R_SH_TLS_IE_32:
	  BFD_ASSERT (htab);
	  check_segment[0] = check_segment[1] = -1;
	  r_type = sh_elf_optimized_tls_reloc (info, r_type, h == NULL);
	  got_type = GOT_UNKNOWN;
	  if (h == NULL && local_got_offsets)
	    got_type = sh_elf_local_got_type (input_bfd) [r_symndx];
	  else if (h != NULL)
	    {
	      got_type = sh_elf_hash_entry (h)->got_type;
	      if (! bfd_link_pic (info)
		  && (h->dynindx == -1
		      || h->def_regular))
		r_type = R_SH_TLS_LE_32;
	    }

	  if (r_type == R_SH_TLS_GD_32 && got_type == GOT_TLS_IE)
	    r_type = R_SH_TLS_IE_32;

	  if (r_type == R_SH_TLS_LE_32)
	    {
	      bfd_vma offset;
	      unsigned short insn;

	      if (ELF32_R_TYPE (rel->r_info) == R_SH_TLS_GD_32)
		{
		  /* GD->LE transition:
		       mov.l 1f,r4; mova 2f,r0; mov.l 2f,r1; add r0,r1;
		       jsr @r1; add r12,r4; bra 3f; nop; .align 2;
		       1: .long x$TLSGD; 2: .long __tls_get_addr@PLT; 3:
		     We change it into:
		       mov.l 1f,r4; stc gbr,r0; add r4,r0; nop;
		       nop; nop; ...
		       1: .long x@TPOFF; 2: .long __tls_get_addr@PLT; 3:.  */

		  offset = rel->r_offset;
		  BFD_ASSERT (offset >= 16);
		  /* Size of GD instructions is 16 or 18.  */
		  offset -= 16;
		  insn = bfd_get_16 (input_bfd, contents + offset + 0);
		  if ((insn & 0xff00) == 0xc700)
		    {
		      BFD_ASSERT (offset >= 2);
		      offset -= 2;
		      insn = bfd_get_16 (input_bfd, contents + offset + 0);
		    }

		  BFD_ASSERT ((insn & 0xff00) == 0xd400);
		  insn = bfd_get_16 (input_bfd, contents + offset + 2);
		  BFD_ASSERT ((insn & 0xff00) == 0xc700);
		  insn = bfd_get_16 (input_bfd, contents + offset + 4);
		  BFD_ASSERT ((insn & 0xff00) == 0xd100);
		  insn = bfd_get_16 (input_bfd, contents + offset + 6);
		  BFD_ASSERT (insn == 0x310c);
		  insn = bfd_get_16 (input_bfd, contents + offset + 8);
		  BFD_ASSERT (insn == 0x410b);
		  insn = bfd_get_16 (input_bfd, contents + offset + 10);
		  BFD_ASSERT (insn == 0x34cc);

		  bfd_put_16 (output_bfd, 0x0012, contents + offset + 2);
		  bfd_put_16 (output_bfd, 0x304c, contents + offset + 4);
		  bfd_put_16 (output_bfd, 0x0009, contents + offset + 6);
		  bfd_put_16 (output_bfd, 0x0009, contents + offset + 8);
		  bfd_put_16 (output_bfd, 0x0009, contents + offset + 10);
		}
	      else
		{
		  int target;

		  /* IE->LE transition:
		     mov.l 1f,r0; stc gbr,rN; mov.l @(r0,r12),rM;
		     bra 2f; add ...; .align 2; 1: x@GOTTPOFF; 2:
		     We change it into:
		     mov.l .Ln,rM; stc gbr,rN; nop; ...;
		     1: x@TPOFF; 2:.  */

		  offset = rel->r_offset;
		  BFD_ASSERT (offset >= 16);
		  /* Size of IE instructions is 10 or 12.  */
		  offset -= 10;
		  insn = bfd_get_16 (input_bfd, contents + offset + 0);
		  if ((insn & 0xf0ff) == 0x0012)
		    {
		      BFD_ASSERT (offset >= 2);
		      offset -= 2;
		      insn = bfd_get_16 (input_bfd, contents + offset + 0);
		    }

		  BFD_ASSERT ((insn & 0xff00) == 0xd000);
		  target = insn & 0x00ff;
		  insn = bfd_get_16 (input_bfd, contents + offset + 2);
		  BFD_ASSERT ((insn & 0xf0ff) == 0x0012);
		  insn = bfd_get_16 (input_bfd, contents + offset + 4);
		  BFD_ASSERT ((insn & 0xf0ff) == 0x00ce);
		  insn = 0xd000 | (insn & 0x0f00) | target;
		  bfd_put_16 (output_bfd, insn, contents + offset + 0);
		  bfd_put_16 (output_bfd, 0x0009, contents + offset + 4);
		}

	      bfd_put_32 (output_bfd, tpoff (info, relocation),
			  contents + rel->r_offset);
	      continue;
	    }

	  if (sgot == NULL || sgotplt == NULL)
	    abort ();

	  if (h != NULL)
	    off = h->got.offset;
	  else
	    {
	      if (local_got_offsets == NULL)
		abort ();

	      off = local_got_offsets[r_symndx];
	    }

	  /* Relocate R_SH_TLS_IE_32 directly when statically linking.  */
	  if (r_type == R_SH_TLS_IE_32
	      && ! htab->root.dynamic_sections_created)
	    {
	      off &= ~1;
	      bfd_put_32 (output_bfd, tpoff (info, relocation),
			  sgot->contents + off);
	      bfd_put_32 (output_bfd, sh_elf_got_offset (htab) + off,
			  contents + rel->r_offset);
	      continue;
	    }

	  if ((off & 1) != 0)
	    off &= ~1;
	  else
	    {
	      Elf_Internal_Rela outrel;
	      bfd_byte *loc;
	      int dr_type, indx;

	      outrel.r_offset = (sgot->output_section->vma
				 + sgot->output_offset + off);

	      if (h == NULL || h->dynindx == -1)
		indx = 0;
	      else
		indx = h->dynindx;

	      dr_type = (r_type == R_SH_TLS_GD_32 ? R_SH_TLS_DTPMOD32 :
			 R_SH_TLS_TPOFF32);
	      if (dr_type == R_SH_TLS_TPOFF32 && indx == 0)
		outrel.r_addend = relocation - dtpoff_base (info);
	      else
		outrel.r_addend = 0;
	      outrel.r_info = ELF32_R_INFO (indx, dr_type);
	      loc = srelgot->contents;
	      loc += srelgot->reloc_count++ * sizeof (Elf32_External_Rela);
	      bfd_elf32_swap_reloca_out (output_bfd, &outrel, loc);

	      if (r_type == R_SH_TLS_GD_32)
		{
		  if (indx == 0)
		    {
		      bfd_put_32 (output_bfd,
				  relocation - dtpoff_base (info),
				  sgot->contents + off + 4);
		    }
		  else
		    {
		      outrel.r_info = ELF32_R_INFO (indx,
						    R_SH_TLS_DTPOFF32);
		      outrel.r_offset += 4;
		      outrel.r_addend = 0;
		      srelgot->reloc_count++;
		      loc += sizeof (Elf32_External_Rela);
		      bfd_elf32_swap_reloca_out (output_bfd, &outrel, loc);
		    }
		}

	      if (h != NULL)
		h->got.offset |= 1;
	      else
		local_got_offsets[r_symndx] |= 1;
	    }

	  if (off >= (bfd_vma) -2)
	    abort ();

	  if (r_type == (int) ELF32_R_TYPE (rel->r_info))
	    relocation = sh_elf_got_offset (htab) + off;
	  else
	    {
	      bfd_vma offset;
	      unsigned short insn;

	      /* GD->IE transition:
		   mov.l 1f,r4; mova 2f,r0; mov.l 2f,r1; add r0,r1;
		   jsr @r1; add r12,r4; bra 3f; nop; .align 2;
		   1: .long x$TLSGD; 2: .long __tls_get_addr@PLT; 3:
		 We change it into:
		   mov.l 1f,r0; stc gbr,r4; mov.l @(r0,r12),r0; add r4,r0;
		   nop; nop; bra 3f; nop; .align 2;
		   1: .long x@TPOFF; 2:...; 3:.  */

	      offset = rel->r_offset;
	      BFD_ASSERT (offset >= 16);
	      /* Size of GD instructions is 16 or 18.  */
	      offset -= 16;
	      insn = bfd_get_16 (input_bfd, contents + offset + 0);
	      if ((insn & 0xff00) == 0xc700)
		{
		  BFD_ASSERT (offset >= 2);
		  offset -= 2;
		  insn = bfd_get_16 (input_bfd, contents + offset + 0);
		}

	      BFD_ASSERT ((insn & 0xff00) == 0xd400);

	      /* Replace mov.l 1f,R4 with mov.l 1f,r0.  */
	      bfd_put_16 (output_bfd, insn & 0xf0ff, contents + offset);

	      insn = bfd_get_16 (input_bfd, contents + offset + 2);
	      BFD_ASSERT ((insn & 0xff00) == 0xc700);
	      insn = bfd_get_16 (input_bfd, contents + offset + 4);
	      BFD_ASSERT ((insn & 0xff00) == 0xd100);
	      insn = bfd_get_16 (input_bfd, contents + offset + 6);
	      BFD_ASSERT (insn == 0x310c);
	      insn = bfd_get_16 (input_bfd, contents + offset + 8);
	      BFD_ASSERT (insn == 0x410b);
	      insn = bfd_get_16 (input_bfd, contents + offset + 10);
	      BFD_ASSERT (insn == 0x34cc);

	      bfd_put_16 (output_bfd, 0x0412, contents + offset + 2);
	      bfd_put_16 (output_bfd, 0x00ce, contents + offset + 4);
	      bfd_put_16 (output_bfd, 0x304c, contents + offset + 6);
	      bfd_put_16 (output_bfd, 0x0009, contents + offset + 8);
	      bfd_put_16 (output_bfd, 0x0009, contents + offset + 10);

	      bfd_put_32 (output_bfd, sh_elf_got_offset (htab) + off,
			  contents + rel->r_offset);

	      continue;
	  }

	  addend = rel->r_addend;

	  goto final_link_relocate;

	case R_SH_TLS_LD_32:
	  BFD_ASSERT (htab);
	  check_segment[0] = check_segment[1] = -1;
	  if (! bfd_link_pic (info))
	    {
	      bfd_vma offset;
	      unsigned short insn;

	      /* LD->LE transition:
		   mov.l 1f,r4; mova 2f,r0; mov.l 2f,r1; add r0,r1;
		   jsr @r1; add r12,r4; bra 3f; nop; .align 2;
		   1: .long x$TLSLD; 2: .long __tls_get_addr@PLT; 3:
		 We change it into:
		   stc gbr,r0; nop; nop; nop;
		   nop; nop; bra 3f; ...; 3:.  */

	      offset = rel->r_offset;
	      BFD_ASSERT (offset >= 16);
	      /* Size of LD instructions is 16 or 18.  */
	      offset -= 16;
	      insn = bfd_get_16 (input_bfd, contents + offset + 0);
	      if ((insn & 0xff00) == 0xc700)
		{
		  BFD_ASSERT (offset >= 2);
		  offset -= 2;
		  insn = bfd_get_16 (input_bfd, contents + offset + 0);
		}

	      BFD_ASSERT ((insn & 0xff00) == 0xd400);
	      insn = bfd_get_16 (input_bfd, contents + offset + 2);
	      BFD_ASSERT ((insn & 0xff00) == 0xc700);
	      insn = bfd_get_16 (input_bfd, contents + offset + 4);
	      BFD_ASSERT ((insn & 0xff00) == 0xd100);
	      insn = bfd_get_16 (input_bfd, contents + offset + 6);
	      BFD_ASSERT (insn == 0x310c);
	      insn = bfd_get_16 (input_bfd, contents + offset + 8);
	      BFD_ASSERT (insn == 0x410b);
	      insn = bfd_get_16 (input_bfd, contents + offset + 10);
	      BFD_ASSERT (insn == 0x34cc);

	      bfd_put_16 (output_bfd, 0x0012, contents + offset + 0);
	      bfd_put_16 (output_bfd, 0x0009, contents + offset + 2);
	      bfd_put_16 (output_bfd, 0x0009, contents + offset + 4);
	      bfd_put_16 (output_bfd, 0x0009, contents + offset + 6);
	      bfd_put_16 (output_bfd, 0x0009, contents + offset + 8);
	      bfd_put_16 (output_bfd, 0x0009, contents + offset + 10);

	      continue;
	    }

	  if (sgot == NULL || sgotplt == NULL)
	    abort ();

	  off = htab->tls_ldm_got.offset;
	  if (off & 1)
	    off &= ~1;
	  else
	    {
	      Elf_Internal_Rela outrel;
	      bfd_byte *loc;

	      outrel.r_offset = (sgot->output_section->vma
				 + sgot->output_offset + off);
	      outrel.r_addend = 0;
	      outrel.r_info = ELF32_R_INFO (0, R_SH_TLS_DTPMOD32);
	      loc = srelgot->contents;
	      loc += srelgot->reloc_count++ * sizeof (Elf32_External_Rela);
	      bfd_elf32_swap_reloca_out (output_bfd, &outrel, loc);
	      htab->tls_ldm_got.offset |= 1;
	    }

	  relocation = sh_elf_got_offset (htab) + off;
	  addend = rel->r_addend;

	  goto final_link_relocate;

	case R_SH_TLS_LDO_32:
	  check_segment[0] = check_segment[1] = -1;
	  if (! bfd_link_pic (info))
	    relocation = tpoff (info, relocation);
	  else
	    relocation -= dtpoff_base (info);

	  addend = rel->r_addend;
	  goto final_link_relocate;

	case R_SH_TLS_LE_32:
	  {
	    int indx;
	    Elf_Internal_Rela outrel;
	    bfd_byte *loc;

	    check_segment[0] = check_segment[1] = -1;

	    if (!bfd_link_dll (info))
	      {
		relocation = tpoff (info, relocation);
		addend = rel->r_addend;
		goto final_link_relocate;
	      }

	    if (sreloc == NULL)
	      {
		sreloc = _bfd_elf_get_dynamic_reloc_section
		  (input_bfd, input_section, /*rela?*/ TRUE);
		if (sreloc == NULL)
		  return FALSE;
	      }

	    if (h == NULL || h->dynindx == -1)
	      indx = 0;
	    else
	      indx = h->dynindx;

	    outrel.r_offset = (input_section->output_section->vma
			       + input_section->output_offset
			       + rel->r_offset);
	    outrel.r_info = ELF32_R_INFO (indx, R_SH_TLS_TPOFF32);
	    if (indx == 0)
	      outrel.r_addend = relocation - dtpoff_base (info);
	    else
	      outrel.r_addend = 0;

	    loc = sreloc->contents;
	    loc += sreloc->reloc_count++ * sizeof (Elf32_External_Rela);
	    bfd_elf32_swap_reloca_out (output_bfd, &outrel, loc);
	    continue;
	  }
	}

    relocation_done:
      if (fdpic_p && check_segment[0] != (unsigned) -1
	  && check_segment[0] != check_segment[1])
	{
	  /* We don't want duplicate errors for undefined symbols.  */
	  if (!h || h->root.type != bfd_link_hash_undefined)
	    {
	      if (bfd_link_pic (info))
		{
		  info->callbacks->einfo
		    /* xgettext:c-format */
		    (_("%X%C: relocation to \"%s\" references a different segment\n"),
		     input_bfd, input_section, rel->r_offset, symname);
		  return FALSE;
		}
	      else
		info->callbacks->einfo
		  /* xgettext:c-format */
		  (_("%C: warning: relocation to \"%s\" references a different segment\n"),
		   input_bfd, input_section, rel->r_offset, symname);
	    }

	  elf_elfheader (output_bfd)->e_flags |= EF_SH_PIC;
	}

      if (r != bfd_reloc_ok)
	{
	  switch (r)
	    {
	    default:
	    case bfd_reloc_outofrange:
	      abort ();
	    case bfd_reloc_overflow:
	      {
		const char *name;

		if (h != NULL)
		  name = NULL;
		else
		  {
		    name = (bfd_elf_string_from_elf_section
			    (input_bfd, symtab_hdr->sh_link, sym->st_name));
		    if (name == NULL)
		      return FALSE;
		    if (*name == '\0')
		      name = bfd_section_name (input_bfd, sec);
		  }
		(*info->callbacks->reloc_overflow)
		  (info, (h ? &h->root : NULL), name, howto->name,
		   (bfd_vma) 0, input_bfd, input_section, rel->r_offset);
	      }
	      break;
	    }
	}
    }

  return TRUE;
}

/* This is a version of bfd_generic_get_relocated_section_contents
   which uses sh_elf_relocate_section.  */

static bfd_byte *
sh_elf_get_relocated_section_contents (bfd *output_bfd,
				       struct bfd_link_info *link_info,
				       struct bfd_link_order *link_order,
				       bfd_byte *data,
				       bfd_boolean relocatable,
				       asymbol **symbols)
{
  Elf_Internal_Shdr *symtab_hdr;
  asection *input_section = link_order->u.indirect.section;
  bfd *input_bfd = input_section->owner;
  asection **sections = NULL;
  Elf_Internal_Rela *internal_relocs = NULL;
  Elf_Internal_Sym *isymbuf = NULL;

  /* We only need to handle the case of relaxing, or of having a
     particular set of section contents, specially.  */
  if (relocatable
      || elf_section_data (input_section)->this_hdr.contents == NULL)
    return bfd_generic_get_relocated_section_contents (output_bfd, link_info,
						       link_order, data,
						       relocatable,
						       symbols);

  symtab_hdr = &elf_symtab_hdr (input_bfd);

  memcpy (data, elf_section_data (input_section)->this_hdr.contents,
	  (size_t) input_section->size);

  if ((input_section->flags & SEC_RELOC) != 0
      && input_section->reloc_count > 0)
    {
      asection **secpp;
      Elf_Internal_Sym *isym, *isymend;
      bfd_size_type amt;

      internal_relocs = (_bfd_elf_link_read_relocs
			 (input_bfd, input_section, NULL,
			  (Elf_Internal_Rela *) NULL, FALSE));
      if (internal_relocs == NULL)
	goto error_return;

      if (symtab_hdr->sh_info != 0)
	{
	  isymbuf = (Elf_Internal_Sym *) symtab_hdr->contents;
	  if (isymbuf == NULL)
	    isymbuf = bfd_elf_get_elf_syms (input_bfd, symtab_hdr,
					    symtab_hdr->sh_info, 0,
					    NULL, NULL, NULL);
	  if (isymbuf == NULL)
	    goto error_return;
	}

      amt = symtab_hdr->sh_info;
      amt *= sizeof (asection *);
      sections = (asection **) bfd_malloc (amt);
      if (sections == NULL && amt != 0)
	goto error_return;

      isymend = isymbuf + symtab_hdr->sh_info;
      for (isym = isymbuf, secpp = sections; isym < isymend; ++isym, ++secpp)
	{
	  asection *isec;

	  if (isym->st_shndx == SHN_UNDEF)
	    isec = bfd_und_section_ptr;
	  else if (isym->st_shndx == SHN_ABS)
	    isec = bfd_abs_section_ptr;
	  else if (isym->st_shndx == SHN_COMMON)
	    isec = bfd_com_section_ptr;
	  else
	    isec = bfd_section_from_elf_index (input_bfd, isym->st_shndx);

	  *secpp = isec;
	}

      if (! sh_elf_relocate_section (output_bfd, link_info, input_bfd,
				     input_section, data, internal_relocs,
				     isymbuf, sections))
	goto error_return;

      if (sections != NULL)
	free (sections);
      if (isymbuf != NULL
	  && symtab_hdr->contents != (unsigned char *) isymbuf)
	free (isymbuf);
      if (elf_section_data (input_section)->relocs != internal_relocs)
	free (internal_relocs);
    }

  return data;

 error_return:
  if (sections != NULL)
    free (sections);
  if (isymbuf != NULL
      && symtab_hdr->contents != (unsigned char *) isymbuf)
    free (isymbuf);
  if (internal_relocs != NULL
      && elf_section_data (input_section)->relocs != internal_relocs)
    free (internal_relocs);
  return NULL;
}

/* Return the base VMA address which should be subtracted from real addresses
   when resolving @dtpoff relocation.
   This is PT_TLS segment p_vaddr.  */

static bfd_vma
dtpoff_base (struct bfd_link_info *info)
{
  /* If tls_sec is NULL, we should have signalled an error already.  */
  if (elf_hash_table (info)->tls_sec == NULL)
    return 0;
  return elf_hash_table (info)->tls_sec->vma;
}

/* Return the relocation value for R_SH_TLS_TPOFF32..  */

static bfd_vma
tpoff (struct bfd_link_info *info, bfd_vma address)
{
  /* If tls_sec is NULL, we should have signalled an error already.  */
  if (elf_hash_table (info)->tls_sec == NULL)
    return 0;
  /* SH TLS ABI is variant I and static TLS block start just after tcbhead
     structure which has 2 pointer fields.  */
  return (address - elf_hash_table (info)->tls_sec->vma
	  + align_power ((bfd_vma) 8,
			 elf_hash_table (info)->tls_sec->alignment_power));
}

static asection *
sh_elf_gc_mark_hook (asection *sec,
		     struct bfd_link_info *info,
		     Elf_Internal_Rela *rel,
		     struct elf_link_hash_entry *h,
		     Elf_Internal_Sym *sym)
{
  if (h != NULL)
    switch (ELF32_R_TYPE (rel->r_info))
      {
      case R_SH_GNU_VTINHERIT:
      case R_SH_GNU_VTENTRY:
	return NULL;
      }

  return _bfd_elf_gc_mark_hook (sec, info, rel, h, sym);
}

/* Copy the extra info we tack onto an elf_link_hash_entry.  */

static void
sh_elf_copy_indirect_symbol (struct bfd_link_info *info,
			     struct elf_link_hash_entry *dir,
			     struct elf_link_hash_entry *ind)
{
  struct elf_sh_link_hash_entry *edir, *eind;

  edir = (struct elf_sh_link_hash_entry *) dir;
  eind = (struct elf_sh_link_hash_entry *) ind;

  if (eind->dyn_relocs != NULL)
    {
      if (edir->dyn_relocs != NULL)
	{
	  struct elf_sh_dyn_relocs **pp;
	  struct elf_sh_dyn_relocs *p;

	  /* Add reloc counts against the indirect sym to the direct sym
	     list.  Merge any entries against the same section.  */
	  for (pp = &eind->dyn_relocs; (p = *pp) != NULL; )
	    {
	      struct elf_sh_dyn_relocs *q;

	      for (q = edir->dyn_relocs; q != NULL; q = q->next)
		if (q->sec == p->sec)
		  {
		    q->pc_count += p->pc_count;
		    q->count += p->count;
		    *pp = p->next;
		    break;
		  }
	      if (q == NULL)
		pp = &p->next;
	    }
	  *pp = edir->dyn_relocs;
	}

      edir->dyn_relocs = eind->dyn_relocs;
      eind->dyn_relocs = NULL;
    }
  edir->gotplt_refcount = eind->gotplt_refcount;
  eind->gotplt_refcount = 0;
#ifdef INCLUDE_SHMEDIA
  edir->datalabel_got.refcount += eind->datalabel_got.refcount;
  eind->datalabel_got.refcount = 0;
#endif
  edir->funcdesc.refcount += eind->funcdesc.refcount;
  eind->funcdesc.refcount = 0;
  edir->abs_funcdesc_refcount += eind->abs_funcdesc_refcount;
  eind->abs_funcdesc_refcount = 0;

  if (ind->root.type == bfd_link_hash_indirect
      && dir->got.refcount <= 0)
    {
      edir->got_type = eind->got_type;
      eind->got_type = GOT_UNKNOWN;
    }

  if (ind->root.type != bfd_link_hash_indirect
      && dir->dynamic_adjusted)
    {
      /* If called to transfer flags for a weakdef during processing
	 of elf_adjust_dynamic_symbol, don't copy non_got_ref.
	 We clear it ourselves for ELIMINATE_COPY_RELOCS.  */
      if (dir->versioned != versioned_hidden)
	dir->ref_dynamic |= ind->ref_dynamic;
      dir->ref_regular |= ind->ref_regular;
      dir->ref_regular_nonweak |= ind->ref_regular_nonweak;
      dir->needs_plt |= ind->needs_plt;
    }
  else
    _bfd_elf_link_hash_copy_indirect (info, dir, ind);
}

static int
sh_elf_optimized_tls_reloc (struct bfd_link_info *info, int r_type,
			    int is_local)
{
  if (bfd_link_pic (info))
    return r_type;

  switch (r_type)
    {
    case R_SH_TLS_GD_32:
    case R_SH_TLS_IE_32:
      if (is_local)
	return R_SH_TLS_LE_32;
      return R_SH_TLS_IE_32;
    case R_SH_TLS_LD_32:
      return R_SH_TLS_LE_32;
    }

  return r_type;
}

/* Look through the relocs for a section during the first phase.
   Since we don't do .gots or .plts, we just need to consider the
   virtual table relocs for gc.  */

static bfd_boolean
sh_elf_check_relocs (bfd *abfd, struct bfd_link_info *info, asection *sec,
		     const Elf_Internal_Rela *relocs)
{
  Elf_Internal_Shdr *symtab_hdr;
  struct elf_link_hash_entry **sym_hashes;
  struct elf_sh_link_hash_table *htab;
  const Elf_Internal_Rela *rel;
  const Elf_Internal_Rela *rel_end;
  asection *sreloc;
  unsigned int r_type;
  enum got_type got_type, old_got_type;

  sreloc = NULL;

  if (bfd_link_relocatable (info))
    return TRUE;

  BFD_ASSERT (is_sh_elf (abfd));

  symtab_hdr = &elf_symtab_hdr (abfd);
  sym_hashes = elf_sym_hashes (abfd);

  htab = sh_elf_hash_table (info);
  if (htab == NULL)
    return FALSE;

  rel_end = relocs + sec->reloc_count;
  for (rel = relocs; rel < rel_end; rel++)
    {
      struct elf_link_hash_entry *h;
      unsigned long r_symndx;
#ifdef INCLUDE_SHMEDIA
      int seen_stt_datalabel = 0;
#endif

      r_symndx = ELF32_R_SYM (rel->r_info);
      r_type = ELF32_R_TYPE (rel->r_info);

      if (r_symndx < symtab_hdr->sh_info)
	h = NULL;
      else
	{
	  h = sym_hashes[r_symndx - symtab_hdr->sh_info];
	  while (h->root.type == bfd_link_hash_indirect
		 || h->root.type == bfd_link_hash_warning)
	    {
#ifdef INCLUDE_SHMEDIA
	      seen_stt_datalabel |= h->type == STT_DATALABEL;
#endif
	      h = (struct elf_link_hash_entry *) h->root.u.i.link;
	    }
	}

      r_type = sh_elf_optimized_tls_reloc (info, r_type, h == NULL);
      if (! bfd_link_pic (info)
	  && r_type == R_SH_TLS_IE_32
	  && h != NULL
	  && h->root.type != bfd_link_hash_undefined
	  && h->root.type != bfd_link_hash_undefweak
	  && (h->dynindx == -1
	      || h->def_regular))
	r_type = R_SH_TLS_LE_32;

      if (htab->fdpic_p)
	switch (r_type)
	  {
	  case R_SH_GOTOFFFUNCDESC:
	  case R_SH_GOTOFFFUNCDESC20:
	  case R_SH_FUNCDESC:
	  case R_SH_GOTFUNCDESC:
	  case R_SH_GOTFUNCDESC20:
	    if (h != NULL)
	      {
		if (h->dynindx == -1)
		  switch (ELF_ST_VISIBILITY (h->other))
		    {
		    case STV_INTERNAL:
		    case STV_HIDDEN:
		      break;
		    default:
		      bfd_elf_link_record_dynamic_symbol (info, h);
		      break;
		    }
	      }
	    break;
	  }

      /* Some relocs require a global offset table.  */
      if (htab->root.sgot == NULL)
	{
	  switch (r_type)
	    {
	    case R_SH_DIR32:
	      /* This may require an rofixup.  */
	      if (!htab->fdpic_p)
		break;
	      /* Fall through.  */
	    case R_SH_GOTPLT32:
	    case R_SH_GOT32:
	    case R_SH_GOT20:
	    case R_SH_GOTOFF:
	    case R_SH_GOTOFF20:
	    case R_SH_FUNCDESC:
	    case R_SH_GOTFUNCDESC:
	    case R_SH_GOTFUNCDESC20:
	    case R_SH_GOTOFFFUNCDESC:
	    case R_SH_GOTOFFFUNCDESC20:
	    case R_SH_GOTPC:
#ifdef INCLUDE_SHMEDIA
	    case R_SH_GOTPLT_LOW16:
	    case R_SH_GOTPLT_MEDLOW16:
	    case R_SH_GOTPLT_MEDHI16:
	    case R_SH_GOTPLT_HI16:
	    case R_SH_GOTPLT10BY4:
	    case R_SH_GOTPLT10BY8:
	    case R_SH_GOT_LOW16:
	    case R_SH_GOT_MEDLOW16:
	    case R_SH_GOT_MEDHI16:
	    case R_SH_GOT_HI16:
	    case R_SH_GOT10BY4:
	    case R_SH_GOT10BY8:
	    case R_SH_GOTOFF_LOW16:
	    case R_SH_GOTOFF_MEDLOW16:
	    case R_SH_GOTOFF_MEDHI16:
	    case R_SH_GOTOFF_HI16:
	    case R_SH_GOTPC_LOW16:
	    case R_SH_GOTPC_MEDLOW16:
	    case R_SH_GOTPC_MEDHI16:
	    case R_SH_GOTPC_HI16:
#endif
	    case R_SH_TLS_GD_32:
	    case R_SH_TLS_LD_32:
	    case R_SH_TLS_IE_32:
	      if (htab->root.dynobj == NULL)
		htab->root.dynobj = abfd;
	      if (!create_got_section (htab->root.dynobj, info))
		return FALSE;
	      break;

	    default:
	      break;
	    }
	}

      switch (r_type)
	{
	  /* This relocation describes the C++ object vtable hierarchy.
	     Reconstruct it for later use during GC.  */
	case R_SH_GNU_VTINHERIT:
	  if (!bfd_elf_gc_record_vtinherit (abfd, sec, h, rel->r_offset))
	    return FALSE;
	  break;

	  /* This relocation describes which C++ vtable entries are actually
	     used.  Record for later use during GC.  */
	case R_SH_GNU_VTENTRY:
	  BFD_ASSERT (h != NULL);
	  if (h != NULL
	      && !bfd_elf_gc_record_vtentry (abfd, sec, h, rel->r_addend))
	    return FALSE;
	  break;

	case R_SH_TLS_IE_32:
	  if (bfd_link_pic (info))
	    info->flags |= DF_STATIC_TLS;

	  /* FALLTHROUGH */
	force_got:
	case R_SH_TLS_GD_32:
	case R_SH_GOT32:
	case R_SH_GOT20:
#ifdef INCLUDE_SHMEDIA
	case R_SH_GOT_LOW16:
	case R_SH_GOT_MEDLOW16:
	case R_SH_GOT_MEDHI16:
	case R_SH_GOT_HI16:
	case R_SH_GOT10BY4:
	case R_SH_GOT10BY8:
#endif
	case R_SH_GOTFUNCDESC:
	case R_SH_GOTFUNCDESC20:
	  switch (r_type)
	    {
	    default:
	      got_type = GOT_NORMAL;
	      break;
	    case R_SH_TLS_GD_32:
	      got_type = GOT_TLS_GD;
	      break;
	    case R_SH_TLS_IE_32:
	      got_type = GOT_TLS_IE;
	      break;
	    case R_SH_GOTFUNCDESC:
	    case R_SH_GOTFUNCDESC20:
	      got_type = GOT_FUNCDESC;
	      break;
	    }

	  if (h != NULL)
	    {
#ifdef INCLUDE_SHMEDIA
	      if (seen_stt_datalabel)
		{
		  struct elf_sh_link_hash_entry *eh
		    = (struct elf_sh_link_hash_entry *) h;

		  eh->datalabel_got.refcount += 1;
		}
	      else
#endif
		h->got.refcount += 1;
	      old_got_type = sh_elf_hash_entry (h)->got_type;
	    }
	  else
	    {
	      bfd_signed_vma *local_got_refcounts;

	      /* This is a global offset table entry for a local
		 symbol.  */
	      local_got_refcounts = elf_local_got_refcounts (abfd);
	      if (local_got_refcounts == NULL)
		{
		  bfd_size_type size;

		  size = symtab_hdr->sh_info;
		  size *= sizeof (bfd_signed_vma);
#ifdef INCLUDE_SHMEDIA
		  /* Reserve space for both the datalabel and
		     codelabel local GOT offsets.  */
		  size *= 2;
#endif
		  size += symtab_hdr->sh_info;
		  local_got_refcounts = ((bfd_signed_vma *)
					 bfd_zalloc (abfd, size));
		  if (local_got_refcounts == NULL)
		    return FALSE;
		  elf_local_got_refcounts (abfd) = local_got_refcounts;
#ifdef 	INCLUDE_SHMEDIA
		  /* Take care of both the datalabel and codelabel local
		     GOT offsets.  */
		  sh_elf_local_got_type (abfd)
		    = (char *) (local_got_refcounts + 2 * symtab_hdr->sh_info);
#else
		  sh_elf_local_got_type (abfd)
		    = (char *) (local_got_refcounts + symtab_hdr->sh_info);
#endif
		}
#ifdef INCLUDE_SHMEDIA
	      if (rel->r_addend & 1)
		local_got_refcounts[symtab_hdr->sh_info + r_symndx] += 1;
	      else
#endif
		local_got_refcounts[r_symndx] += 1;
	      old_got_type = sh_elf_local_got_type (abfd) [r_symndx];
	    }

	  /* If a TLS symbol is accessed using IE at least once,
	     there is no point to use dynamic model for it.  */
	  if (old_got_type != got_type && old_got_type != GOT_UNKNOWN
	      && (old_got_type != GOT_TLS_GD || got_type != GOT_TLS_IE))
	    {
	      if (old_got_type == GOT_TLS_IE && got_type == GOT_TLS_GD)
		got_type = GOT_TLS_IE;
	      else
		{
		  if ((old_got_type == GOT_FUNCDESC || got_type == GOT_FUNCDESC)
		      && (old_got_type == GOT_NORMAL || got_type == GOT_NORMAL))
		    _bfd_error_handler
		      /* xgettext:c-format */
		      (_("%B: `%s' accessed both as normal and FDPIC symbol"),
		       abfd, h->root.root.string);
		  else if (old_got_type == GOT_FUNCDESC
			   || got_type == GOT_FUNCDESC)
		    _bfd_error_handler
		      /* xgettext:c-format */
		      (_("%B: `%s' accessed both as FDPIC and thread local symbol"),
		       abfd, h->root.root.string);
		  else
		    _bfd_error_handler
		      /* xgettext:c-format */
		      (_("%B: `%s' accessed both as normal and thread local symbol"),
		       abfd, h->root.root.string);
		  return FALSE;
		}
	    }

	  if (old_got_type != got_type)
	    {
	      if (h != NULL)
		sh_elf_hash_entry (h)->got_type = got_type;
	      else
		sh_elf_local_got_type (abfd) [r_symndx] = got_type;
	    }

	  break;

	case R_SH_TLS_LD_32:
	  sh_elf_hash_table(info)->tls_ldm_got.refcount += 1;
	  break;

	case R_SH_FUNCDESC:
	case R_SH_GOTOFFFUNCDESC:
	case R_SH_GOTOFFFUNCDESC20:
	  if (rel->r_addend)
	    {
	      _bfd_error_handler
		(_("%B: Function descriptor relocation with non-zero addend"),
		 abfd);
	      return FALSE;
	    }

	  if (h == NULL)
	    {
	      union gotref *local_funcdesc;

	      /* We need a function descriptor for a local symbol.  */
	      local_funcdesc = sh_elf_local_funcdesc (abfd);
	      if (local_funcdesc == NULL)
		{
		  bfd_size_type size;

		  size = symtab_hdr->sh_info * sizeof (union gotref);
#ifdef INCLUDE_SHMEDIA
		  /* Count datalabel local GOT.  */
		  size *= 2;
#endif
		  local_funcdesc = (union gotref *) bfd_zalloc (abfd, size);
		  if (local_funcdesc == NULL)
		    return FALSE;
		  sh_elf_local_funcdesc (abfd) = local_funcdesc;
		}
	      local_funcdesc[r_symndx].refcount += 1;

	      if (r_type == R_SH_FUNCDESC)
		{
		  if (!bfd_link_pic (info))
		    htab->srofixup->size += 4;
		  else
		    htab->root.srelgot->size += sizeof (Elf32_External_Rela);
		}
	    }
	  else
	    {
	      sh_elf_hash_entry (h)->funcdesc.refcount++;
	      if (r_type == R_SH_FUNCDESC)
		sh_elf_hash_entry (h)->abs_funcdesc_refcount++;

	      /* If there is a function descriptor reference, then
		 there should not be any non-FDPIC references.  */
	      old_got_type = sh_elf_hash_entry (h)->got_type;
	      if (old_got_type != GOT_FUNCDESC && old_got_type != GOT_UNKNOWN)
		{
		  if (old_got_type == GOT_NORMAL)
		    _bfd_error_handler
		      /* xgettext:c-format */
		      (_("%B: `%s' accessed both as normal and FDPIC symbol"),
		       abfd, h->root.root.string);
		  else
		    _bfd_error_handler
		      /* xgettext:c-format */
		      (_("%B: `%s' accessed both as FDPIC and thread local symbol"),
		       abfd, h->root.root.string);
		}
	    }
	  break;

	case R_SH_GOTPLT32:
#ifdef INCLUDE_SHMEDIA
	case R_SH_GOTPLT_LOW16:
	case R_SH_GOTPLT_MEDLOW16:
	case R_SH_GOTPLT_MEDHI16:
	case R_SH_GOTPLT_HI16:
	case R_SH_GOTPLT10BY4:
	case R_SH_GOTPLT10BY8:
#endif
	  /* If this is a local symbol, we resolve it directly without
	     creating a procedure linkage table entry.  */

	  if (h == NULL
	      || h->forced_local
	      || ! bfd_link_pic (info)
	      || info->symbolic
	      || h->dynindx == -1)
	    goto force_got;

	  h->needs_plt = 1;
	  h->plt.refcount += 1;
	  ((struct elf_sh_link_hash_entry *) h)->gotplt_refcount += 1;

	  break;

	case R_SH_PLT32:
#ifdef INCLUDE_SHMEDIA
	case R_SH_PLT_LOW16:
	case R_SH_PLT_MEDLOW16:
	case R_SH_PLT_MEDHI16:
	case R_SH_PLT_HI16:
#endif
	  /* This symbol requires a procedure linkage table entry.  We
	     actually build the entry in adjust_dynamic_symbol,
	     because this might be a case of linking PIC code which is
	     never referenced by a dynamic object, in which case we
	     don't need to generate a procedure linkage table entry
	     after all.  */

	  /* If this is a local symbol, we resolve it directly without
	     creating a procedure linkage table entry.  */
	  if (h == NULL)
	    continue;

	  if (h->forced_local)
	    break;

	  h->needs_plt = 1;
	  h->plt.refcount += 1;
	  break;

	case R_SH_DIR32:
	case R_SH_REL32:
#ifdef INCLUDE_SHMEDIA
	case R_SH_IMM_LOW16_PCREL:
	case R_SH_IMM_MEDLOW16_PCREL:
	case R_SH_IMM_MEDHI16_PCREL:
	case R_SH_IMM_HI16_PCREL:
#endif
	  if (h != NULL && ! bfd_link_pic (info))
	    {
	      h->non_got_ref = 1;
	      h->plt.refcount += 1;
	    }

	  /* If we are creating a shared library, and this is a reloc
	     against a global symbol, or a non PC relative reloc
	     against a local symbol, then we need to copy the reloc
	     into the shared library.  However, if we are linking with
	     -Bsymbolic, we do not need to copy a reloc against a
	     global symbol which is defined in an object we are
	     including in the link (i.e., DEF_REGULAR is set).  At
	     this point we have not seen all the input files, so it is
	     possible that DEF_REGULAR is not set now but will be set
	     later (it is never cleared).  We account for that
	     possibility below by storing information in the
	     dyn_relocs field of the hash table entry. A similar
	     situation occurs when creating shared libraries and symbol
	     visibility changes render the symbol local.

	     If on the other hand, we are creating an executable, we
	     may need to keep relocations for symbols satisfied by a
	     dynamic library if we manage to avoid copy relocs for the
	     symbol.  */
	  if ((bfd_link_pic (info)
	       && (sec->flags & SEC_ALLOC) != 0
	       && (r_type != R_SH_REL32
		   || (h != NULL
		       && (! info->symbolic
			   || h->root.type == bfd_link_hash_defweak
			   || !h->def_regular))))
	      || (! bfd_link_pic (info)
		  && (sec->flags & SEC_ALLOC) != 0
		  && h != NULL
		  && (h->root.type == bfd_link_hash_defweak
		      || !h->def_regular)))
	    {
	      struct elf_sh_dyn_relocs *p;
	      struct elf_sh_dyn_relocs **head;

	      if (htab->root.dynobj == NULL)
		htab->root.dynobj = abfd;

	      /* When creating a shared object, we must copy these
		 reloc types into the output file.  We create a reloc
		 section in dynobj and make room for this reloc.  */
	      if (sreloc == NULL)
		{
		  sreloc = _bfd_elf_make_dynamic_reloc_section
		    (sec, htab->root.dynobj, 2, abfd, /*rela?*/ TRUE);

		  if (sreloc == NULL)
		    return FALSE;
		}

	      /* If this is a global symbol, we count the number of
		 relocations we need for this symbol.  */
	      if (h != NULL)
		head = &((struct elf_sh_link_hash_entry *) h)->dyn_relocs;
	      else
		{
		  /* Track dynamic relocs needed for local syms too.  */
		  asection *s;
		  void *vpp;
		  Elf_Internal_Sym *isym;

		  isym = bfd_sym_from_r_symndx (&htab->sym_cache,
						abfd, r_symndx);
		  if (isym == NULL)
		    return FALSE;

		  s = bfd_section_from_elf_index (abfd, isym->st_shndx);
		  if (s == NULL)
		    s = sec;

		  vpp = &elf_section_data (s)->local_dynrel;
		  head = (struct elf_sh_dyn_relocs **) vpp;
		}

	      p = *head;
	      if (p == NULL || p->sec != sec)
		{
		  bfd_size_type amt = sizeof (*p);
		  p = bfd_alloc (htab->root.dynobj, amt);
		  if (p == NULL)
		    return FALSE;
		  p->next = *head;
		  *head = p;
		  p->sec = sec;
		  p->count = 0;
		  p->pc_count = 0;
		}

	      p->count += 1;
	      if (r_type == R_SH_REL32
#ifdef INCLUDE_SHMEDIA
		  || r_type == R_SH_IMM_LOW16_PCREL
		  || r_type == R_SH_IMM_MEDLOW16_PCREL
		  || r_type == R_SH_IMM_MEDHI16_PCREL
		  || r_type == R_SH_IMM_HI16_PCREL
#endif
		  )
		p->pc_count += 1;
	    }

	  /* Allocate the fixup regardless of whether we need a relocation.
	     If we end up generating the relocation, we'll unallocate the
	     fixup.  */
	  if (htab->fdpic_p && !bfd_link_pic (info)
	      && r_type == R_SH_DIR32
	      && (sec->flags & SEC_ALLOC) != 0)
	    htab->srofixup->size += 4;
	  break;

	case R_SH_TLS_LE_32:
	  if (bfd_link_dll (info))
	    {
	      _bfd_error_handler
		(_("%B: TLS local exec code cannot be linked into shared objects"),
		 abfd);
	      return FALSE;
	    }

	  break;

	case R_SH_TLS_LDO_32:
	  /* Nothing to do.  */
	  break;

	default:
	  break;
	}
    }

  return TRUE;
}

#ifndef sh_elf_set_mach_from_flags
static unsigned int sh_ef_bfd_table[] = { EF_SH_BFD_TABLE };

static bfd_boolean
sh_elf_set_mach_from_flags (bfd *abfd)
{
  flagword flags = elf_elfheader (abfd)->e_flags & EF_SH_MACH_MASK;

  if (flags >= ARRAY_SIZE (sh_ef_bfd_table))
    return FALSE;

  if (sh_ef_bfd_table[flags] == 0)
    return FALSE;

  bfd_default_set_arch_mach (abfd, bfd_arch_sh, sh_ef_bfd_table[flags]);

  return TRUE;
}


/* Reverse table lookup for sh_ef_bfd_table[].
   Given a bfd MACH value from archures.c
   return the equivalent ELF flags from the table.
   Return -1 if no match is found.  */

int
sh_elf_get_flags_from_mach (unsigned long mach)
{
  int i = ARRAY_SIZE (sh_ef_bfd_table) - 1;

  for (; i>0; i--)
    if (sh_ef_bfd_table[i] == mach)
      return i;

  /* shouldn't get here */
  BFD_FAIL();

  return -1;
}
#endif /* not sh_elf_set_mach_from_flags */

#ifndef sh_elf_copy_private_data
/* Copy backend specific data from one object module to another */

static bfd_boolean
sh_elf_copy_private_data (bfd * ibfd, bfd * obfd)
{
  if (! is_sh_elf (ibfd) || ! is_sh_elf (obfd))
    return TRUE;

  if (! _bfd_elf_copy_private_bfd_data (ibfd, obfd))
    return FALSE;

  return sh_elf_set_mach_from_flags (obfd);
}
#endif /* not sh_elf_copy_private_data */

#ifndef sh_elf_merge_private_data

/* This function returns the ELF architecture number that
   corresponds to the given arch_sh* flags.  */

int
sh_find_elf_flags (unsigned int arch_set)
{
  extern unsigned long sh_get_bfd_mach_from_arch_set (unsigned int);
  unsigned long bfd_mach = sh_get_bfd_mach_from_arch_set (arch_set);

  return sh_elf_get_flags_from_mach (bfd_mach);
}

/* Merge the architecture type of two BFD files, such that the
   resultant architecture supports all the features required
   by the two input BFDs.
   If the input BFDs are multually incompatible - i.e. one uses
   DSP while the other uses FPU - or there is no known architecture
   that fits the requirements then an error is emitted.  */

static bfd_boolean
sh_merge_bfd_arch (bfd *ibfd, struct bfd_link_info *info)
{
  bfd *obfd = info->output_bfd;
  unsigned int old_arch, new_arch, merged_arch;

  if (! _bfd_generic_verify_endian_match (ibfd, info))
    return FALSE;

  old_arch = sh_get_arch_up_from_bfd_mach (bfd_get_mach (obfd));
  new_arch = sh_get_arch_up_from_bfd_mach (bfd_get_mach (ibfd));

  merged_arch = SH_MERGE_ARCH_SET (old_arch, new_arch);

  if (!SH_VALID_CO_ARCH_SET (merged_arch))
    {
      _bfd_error_handler
	/* xgettext:c-format */
	(_("%B: uses %s instructions while previous modules "
	   "use %s instructions"),
	 ibfd,
	 SH_ARCH_SET_HAS_DSP (new_arch) ? "dsp" : "floating point",
	 SH_ARCH_SET_HAS_DSP (new_arch) ? "floating point" : "dsp");
      bfd_set_error (bfd_error_bad_value);
      return FALSE;
    }
  else if (!SH_VALID_ARCH_SET (merged_arch))
    {
      _bfd_error_handler
	/* xgettext:c-format */
	(_("internal error: merge of architecture '%s' with "
	   "architecture '%s' produced unknown architecture"),
	 bfd_printable_name (obfd),
	 bfd_printable_name (ibfd));
      bfd_set_error (bfd_error_bad_value);
      return FALSE;
    }

  bfd_default_set_arch_mach (obfd, bfd_arch_sh,
			     sh_get_bfd_mach_from_arch_set (merged_arch));

  return TRUE;
}

/* This routine initialises the elf flags when required and
   calls sh_merge_bfd_arch() to check dsp/fpu compatibility.  */

static bfd_boolean
sh_elf_merge_private_data (bfd *ibfd, struct bfd_link_info *info)
{
  bfd *obfd = info->output_bfd;

  if (! is_sh_elf (ibfd) || ! is_sh_elf (obfd))
    return TRUE;

  if (! elf_flags_init (obfd))
    {
      /* This happens when ld starts out with a 'blank' output file.  */
      elf_flags_init (obfd) = TRUE;
      elf_elfheader (obfd)->e_flags = elf_elfheader (ibfd)->e_flags;
      sh_elf_set_mach_from_flags (obfd);
      if (elf_elfheader (obfd)->e_flags & EF_SH_FDPIC)
	elf_elfheader (obfd)->e_flags &= ~EF_SH_PIC;
    }

  if (! sh_merge_bfd_arch (ibfd, info))
    {
      _bfd_error_handler (_("%B: uses instructions which are incompatible "
			    "with instructions used in previous modules"),
			  ibfd);
      bfd_set_error (bfd_error_bad_value);
      return FALSE;
    }

  elf_elfheader (obfd)->e_flags &= ~EF_SH_MACH_MASK;
  elf_elfheader (obfd)->e_flags |=
    sh_elf_get_flags_from_mach (bfd_get_mach (obfd));

  if (fdpic_object_p (ibfd) != fdpic_object_p (obfd))
    {
      _bfd_error_handler (_("%B: attempt to mix FDPIC and non-FDPIC objects"),
			  ibfd);
      bfd_set_error (bfd_error_bad_value);
      return FALSE;
    }

  return TRUE;
}
#endif /* not sh_elf_merge_private_data */

/* Override the generic function because we need to store sh_elf_obj_tdata
   as the specific tdata.  We set also the machine architecture from flags
   here.  */

static bfd_boolean
sh_elf_object_p (bfd *abfd)
{
  if (! sh_elf_set_mach_from_flags (abfd))
    return FALSE;

  return (((elf_elfheader (abfd)->e_flags & EF_SH_FDPIC) != 0)
	  == fdpic_object_p (abfd));
}

/* Finish up dynamic symbol handling.  We set the contents of various
   dynamic sections here.  */

static bfd_boolean
sh_elf_finish_dynamic_symbol (bfd *output_bfd, struct bfd_link_info *info,
			      struct elf_link_hash_entry *h,
			      Elf_Internal_Sym *sym)
{
  struct elf_sh_link_hash_table *htab;

  htab = sh_elf_hash_table (info);
  if (htab == NULL)
    return FALSE;

  if (h->plt.offset != (bfd_vma) -1)
    {
      asection *splt;
      asection *sgotplt;
      asection *srelplt;

      bfd_vma plt_index;
      bfd_vma got_offset;
      Elf_Internal_Rela rel;
      bfd_byte *loc;
      const struct elf_sh_plt_info *plt_info;

      /* This symbol has an entry in the procedure linkage table.  Set
	 it up.  */

      BFD_ASSERT (h->dynindx != -1);

      splt = htab->root.splt;
      sgotplt = htab->root.sgotplt;
      srelplt = htab->root.srelplt;
      BFD_ASSERT (splt != NULL && sgotplt != NULL && srelplt != NULL);

      /* Get the index in the procedure linkage table which
	 corresponds to this symbol.  This is the index of this symbol
	 in all the symbols for which we are making plt entries.  The
	 first entry in the procedure linkage table is reserved.  */
      plt_index = get_plt_index (htab->plt_info, h->plt.offset);

      plt_info = htab->plt_info;
      if (plt_info->short_plt != NULL && plt_index <= MAX_SHORT_PLT)
	plt_info = plt_info->short_plt;

      /* Get the offset into the .got table of the entry that
	 corresponds to this function.  */
      if (htab->fdpic_p)
	/* The offset must be relative to the GOT symbol, twelve bytes
	   before the end of .got.plt.  Each descriptor is eight
	   bytes.  */
	got_offset = plt_index * 8 + 12 - sgotplt->size;
      else
	/* Each .got entry is 4 bytes.  The first three are
	   reserved.  */
	got_offset = (plt_index + 3) * 4;

#ifdef GOT_BIAS
      if (bfd_link_pic (info))
	got_offset -= GOT_BIAS;
#endif

      /* Fill in the entry in the procedure linkage table.  */
      memcpy (splt->contents + h->plt.offset,
	      plt_info->symbol_entry,
	      plt_info->symbol_entry_size);

      if (bfd_link_pic (info) || htab->fdpic_p)
	{
	  if (plt_info->symbol_fields.got20)
	    {
	      bfd_reloc_status_type r;
	      r = install_movi20_field (output_bfd, got_offset,
					splt->owner, splt, splt->contents,
					h->plt.offset
					+ plt_info->symbol_fields.got_entry);
	      BFD_ASSERT (r == bfd_reloc_ok);
	    }
	  else
	    install_plt_field (output_bfd, FALSE, got_offset,
			       (splt->contents
				+ h->plt.offset
				+ plt_info->symbol_fields.got_entry));
	}
      else
	{
	  BFD_ASSERT (!plt_info->symbol_fields.got20);

	  install_plt_field (output_bfd, FALSE,
			     (sgotplt->output_section->vma
			      + sgotplt->output_offset
			      + got_offset),
			     (splt->contents
			      + h->plt.offset
			      + plt_info->symbol_fields.got_entry));
	  if (htab->vxworks_p)
	    {
	      unsigned int reachable_plts, plts_per_4k;
	      int distance;

	      /* Divide the PLT into groups.  The first group contains
		 REACHABLE_PLTS entries and the other groups contain
		 PLTS_PER_4K entries.  Entries in the first group can
		 branch directly to .plt; those in later groups branch
		 to the last element of the previous group.  */
	      /* ??? It would be better to create multiple copies of
		 the common resolver stub.  */
	      reachable_plts = ((4096
				 - plt_info->plt0_entry_size
				 - (plt_info->symbol_fields.plt + 4))
				/ plt_info->symbol_entry_size) + 1;
	      plts_per_4k = (4096 / plt_info->symbol_entry_size);
	      if (plt_index < reachable_plts)
		distance = -(h->plt.offset
			     + plt_info->symbol_fields.plt);
	      else
		distance = -(((plt_index - reachable_plts) % plts_per_4k + 1)
			     * plt_info->symbol_entry_size);

	      /* Install the 'bra' with this offset.  */
	      bfd_put_16 (output_bfd,
			  0xa000 | (0x0fff & ((distance - 4) / 2)),
			  (splt->contents
			   + h->plt.offset
			   + plt_info->symbol_fields.plt));
	    }
	  else
	    install_plt_field (output_bfd, TRUE,
			       splt->output_section->vma + splt->output_offset,
			       (splt->contents
				+ h->plt.offset
				+ plt_info->symbol_fields.plt));
	}

      /* Make got_offset relative to the start of .got.plt.  */
#ifdef GOT_BIAS
      if (bfd_link_pic (info))
	got_offset += GOT_BIAS;
#endif
      if (htab->fdpic_p)
	got_offset = plt_index * 8;

      if (plt_info->symbol_fields.reloc_offset != MINUS_ONE)
	install_plt_field (output_bfd, FALSE,
			   plt_index * sizeof (Elf32_External_Rela),
			   (splt->contents
			    + h->plt.offset
			    + plt_info->symbol_fields.reloc_offset));

      /* Fill in the entry in the global offset table.  */
      bfd_put_32 (output_bfd,
		  (splt->output_section->vma
		   + splt->output_offset
		   + h->plt.offset
		   + plt_info->symbol_resolve_offset),
		  sgotplt->contents + got_offset);
      if (htab->fdpic_p)
	bfd_put_32 (output_bfd,
		    sh_elf_osec_to_segment (output_bfd, splt->output_section),
		    sgotplt->contents + got_offset + 4);

      /* Fill in the entry in the .rela.plt section.  */
      rel.r_offset = (sgotplt->output_section->vma
		      + sgotplt->output_offset
		      + got_offset);
      if (htab->fdpic_p)
	rel.r_info = ELF32_R_INFO (h->dynindx, R_SH_FUNCDESC_VALUE);
      else
	rel.r_info = ELF32_R_INFO (h->dynindx, R_SH_JMP_SLOT);
      rel.r_addend = 0;
#ifdef GOT_BIAS
      rel.r_addend = GOT_BIAS;
#endif
      loc = srelplt->contents + plt_index * sizeof (Elf32_External_Rela);
      bfd_elf32_swap_reloca_out (output_bfd, &rel, loc);

      if (htab->vxworks_p && !bfd_link_pic (info))
	{
	  /* Create the .rela.plt.unloaded relocations for this PLT entry.
	     Begin by pointing LOC to the first such relocation.  */
	  loc = (htab->srelplt2->contents
		 + (plt_index * 2 + 1) * sizeof (Elf32_External_Rela));

	  /* Create a .rela.plt.unloaded R_SH_DIR32 relocation
	     for the PLT entry's pointer to the .got.plt entry.  */
	  rel.r_offset = (splt->output_section->vma
			  + splt->output_offset
			  + h->plt.offset
			  + plt_info->symbol_fields.got_entry);
	  rel.r_info = ELF32_R_INFO (htab->root.hgot->indx, R_SH_DIR32);
	  rel.r_addend = got_offset;
	  bfd_elf32_swap_reloca_out (output_bfd, &rel, loc);
	  loc += sizeof (Elf32_External_Rela);

	  /* Create a .rela.plt.unloaded R_SH_DIR32 relocation for
	     the .got.plt entry, which initially points to .plt.  */
	  rel.r_offset = (sgotplt->output_section->vma
			  + sgotplt->output_offset
			  + got_offset);
	  rel.r_info = ELF32_R_INFO (htab->root.hplt->indx, R_SH_DIR32);
	  rel.r_addend = 0;
	  bfd_elf32_swap_reloc_out (output_bfd, &rel, loc);
	}

      if (!h->def_regular)
	{
	  /* Mark the symbol as undefined, rather than as defined in
	     the .plt section.  Leave the value alone.  */
	  sym->st_shndx = SHN_UNDEF;
	}
    }

  if (h->got.offset != (bfd_vma) -1
      && sh_elf_hash_entry (h)->got_type != GOT_TLS_GD
      && sh_elf_hash_entry (h)->got_type != GOT_TLS_IE
      && sh_elf_hash_entry (h)->got_type != GOT_FUNCDESC)
    {
      asection *sgot;
      asection *srelgot;
      Elf_Internal_Rela rel;
      bfd_byte *loc;

      /* This symbol has an entry in the global offset table.  Set it
	 up.  */

      sgot = htab->root.sgot;
      srelgot = htab->root.srelgot;
      BFD_ASSERT (sgot != NULL && srelgot != NULL);

      rel.r_offset = (sgot->output_section->vma
		      + sgot->output_offset
		      + (h->got.offset &~ (bfd_vma) 1));

      /* If this is a static link, or it is a -Bsymbolic link and the
	 symbol is defined locally or was forced to be local because
	 of a version file, we just want to emit a RELATIVE reloc.
	 The entry in the global offset table will already have been
	 initialized in the relocate_section function.  */
      if (bfd_link_pic (info)
	  && SYMBOL_REFERENCES_LOCAL (info, h))
	{
	  if (htab->fdpic_p)
	    {
	      asection *sec = h->root.u.def.section;
	      int dynindx
		= elf_section_data (sec->output_section)->dynindx;

	      rel.r_info = ELF32_R_INFO (dynindx, R_SH_DIR32);
	      rel.r_addend = (h->root.u.def.value
			      + h->root.u.def.section->output_offset);
	    }
	  else
	    {
	      rel.r_info = ELF32_R_INFO (0, R_SH_RELATIVE);
	      rel.r_addend = (h->root.u.def.value
			      + h->root.u.def.section->output_section->vma
			      + h->root.u.def.section->output_offset);
	    }
	}
      else
	{
	  bfd_put_32 (output_bfd, (bfd_vma) 0, sgot->contents + h->got.offset);
	  rel.r_info = ELF32_R_INFO (h->dynindx, R_SH_GLOB_DAT);
	  rel.r_addend = 0;
	}

      loc = srelgot->contents;
      loc += srelgot->reloc_count++ * sizeof (Elf32_External_Rela);
      bfd_elf32_swap_reloca_out (output_bfd, &rel, loc);
    }

#ifdef INCLUDE_SHMEDIA
  {
    struct elf_sh_link_hash_entry *eh;

    eh = (struct elf_sh_link_hash_entry *) h;
    if (eh->datalabel_got.offset != (bfd_vma) -1)
      {
	asection *sgot;
	asection *srelgot;
	Elf_Internal_Rela rel;
	bfd_byte *loc;

	/* This symbol has a datalabel entry in the global offset table.
	   Set it up.  */

	sgot = htab->root.sgot;
	srelgot = htab->root.srelgot;
	BFD_ASSERT (sgot != NULL && srelgot != NULL);

	rel.r_offset = (sgot->output_section->vma
			+ sgot->output_offset
			+ (eh->datalabel_got.offset &~ (bfd_vma) 1));

	/* If this is a static link, or it is a -Bsymbolic link and the
	   symbol is defined locally or was forced to be local because
	   of a version file, we just want to emit a RELATIVE reloc.
	   The entry in the global offset table will already have been
	   initialized in the relocate_section function.  */
	if (bfd_link_pic (info)
	    && SYMBOL_REFERENCES_LOCAL (info, h))
	  {
	    if (htab->fdpic_p)
	      {
		asection *sec = h->root.u.def.section;
		int dynindx
		  = elf_section_data (sec->output_section)->dynindx;

		rel.r_info = ELF32_R_INFO (dynindx, R_SH_DIR32);
		rel.r_addend = (h->root.u.def.value
				+ h->root.u.def.section->output_offset);
	      }
	    else
	      {
		rel.r_info = ELF32_R_INFO (0, R_SH_RELATIVE);
		rel.r_addend = (h->root.u.def.value
				+ h->root.u.def.section->output_section->vma
				+ h->root.u.def.section->output_offset);
	      }
	  }
	else
	  {
	    bfd_put_32 (output_bfd, (bfd_vma) 0, sgot->contents
			+ eh->datalabel_got.offset);
	    rel.r_info = ELF32_R_INFO (h->dynindx, R_SH_GLOB_DAT);
	    rel.r_addend = 0;
	  }

	loc = srelgot->contents;
	loc += srelgot->reloc_count++ * sizeof (Elf32_External_Rela);
	bfd_elf32_swap_reloca_out (output_bfd, &rel, loc);
      }
  }
#endif

  if (h->needs_copy)
    {
      asection *s;
      Elf_Internal_Rela rel;
      bfd_byte *loc;

      /* This symbol needs a copy reloc.  Set it up.  */

      BFD_ASSERT (h->dynindx != -1
		  && (h->root.type == bfd_link_hash_defined
		      || h->root.type == bfd_link_hash_defweak));

      s = bfd_get_linker_section (htab->root.dynobj, ".rela.bss");
      BFD_ASSERT (s != NULL);

      rel.r_offset = (h->root.u.def.value
		      + h->root.u.def.section->output_section->vma
		      + h->root.u.def.section->output_offset);
      rel.r_info = ELF32_R_INFO (h->dynindx, R_SH_COPY);
      rel.r_addend = 0;
      loc = s->contents + s->reloc_count++ * sizeof (Elf32_External_Rela);
      bfd_elf32_swap_reloca_out (output_bfd, &rel, loc);
    }

  /* Mark _DYNAMIC and _GLOBAL_OFFSET_TABLE_ as absolute.  On VxWorks,
     _GLOBAL_OFFSET_TABLE_ is not absolute: it is relative to the
     ".got" section.  */
  if (h == htab->root.hdynamic
      || (!htab->vxworks_p && h == htab->root.hgot))
    sym->st_shndx = SHN_ABS;

  return TRUE;
}

/* Finish up the dynamic sections.  */

static bfd_boolean
sh_elf_finish_dynamic_sections (bfd *output_bfd, struct bfd_link_info *info)
{
  struct elf_sh_link_hash_table *htab;
  asection *sgotplt;
  asection *sdyn;

  htab = sh_elf_hash_table (info);
  if (htab == NULL)
    return FALSE;

  sgotplt = htab->root.sgotplt;
  sdyn = bfd_get_linker_section (htab->root.dynobj, ".dynamic");

  if (htab->root.dynamic_sections_created)
    {
      asection *splt;
      Elf32_External_Dyn *dyncon, *dynconend;

      BFD_ASSERT (sgotplt != NULL && sdyn != NULL);

      dyncon = (Elf32_External_Dyn *) sdyn->contents;
      dynconend = (Elf32_External_Dyn *) (sdyn->contents + sdyn->size);
      for (; dyncon < dynconend; dyncon++)
	{
	  Elf_Internal_Dyn dyn;
	  asection *s;
#ifdef INCLUDE_SHMEDIA
	  const char *name;
#endif

	  bfd_elf32_swap_dyn_in (htab->root.dynobj, dyncon, &dyn);

	  switch (dyn.d_tag)
	    {
	    default:
	      if (htab->vxworks_p
		  && elf_vxworks_finish_dynamic_entry (output_bfd, &dyn))
		bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
	      break;

#ifdef INCLUDE_SHMEDIA
	    case DT_INIT:
	      name = info->init_function;
	      goto get_sym;

	    case DT_FINI:
	      name = info->fini_function;
	    get_sym:
	      if (dyn.d_un.d_val != 0)
		{
		  struct elf_link_hash_entry *h;

		  h = elf_link_hash_lookup (&htab->root, name,
					    FALSE, FALSE, TRUE);
		  if (h != NULL && (h->other & STO_SH5_ISA32))
		    {
		      dyn.d_un.d_val |= 1;
		      bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
		    }
		}
	      break;
#endif

	    case DT_PLTGOT:
	      BFD_ASSERT (htab->root.hgot != NULL);
	      s = htab->root.hgot->root.u.def.section;
	      dyn.d_un.d_ptr = htab->root.hgot->root.u.def.value
		+ s->output_section->vma + s->output_offset;
	      bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
	      break;

	    case DT_JMPREL:
	      s = htab->root.srelplt->output_section;
	      BFD_ASSERT (s != NULL);
	      dyn.d_un.d_ptr = s->vma;
	      bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
	      break;

	    case DT_PLTRELSZ:
	      s = htab->root.srelplt->output_section;
	      BFD_ASSERT (s != NULL);
	      dyn.d_un.d_val = s->size;
	      bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
	      break;
	    }
	}

      /* Fill in the first entry in the procedure linkage table.  */
      splt = htab->root.splt;
      if (splt && splt->size > 0 && htab->plt_info->plt0_entry)
	{
	  unsigned int i;

	  memcpy (splt->contents,
		  htab->plt_info->plt0_entry,
		  htab->plt_info->plt0_entry_size);
	  for (i = 0; i < ARRAY_SIZE (htab->plt_info->plt0_got_fields); i++)
	    if (htab->plt_info->plt0_got_fields[i] != MINUS_ONE)
	      install_plt_field (output_bfd, FALSE,
				 (sgotplt->output_section->vma
				  + sgotplt->output_offset
				  + (i * 4)),
				 (splt->contents
				  + htab->plt_info->plt0_got_fields[i]));

	  if (htab->vxworks_p)
	    {
	      /* Finalize the .rela.plt.unloaded contents.  */
	      Elf_Internal_Rela rel;
	      bfd_byte *loc;

	      /* Create a .rela.plt.unloaded R_SH_DIR32 relocation for the
		 first PLT entry's pointer to _GLOBAL_OFFSET_TABLE_ + 8.  */
	      loc = htab->srelplt2->contents;
	      rel.r_offset = (splt->output_section->vma
			      + splt->output_offset
			      + htab->plt_info->plt0_got_fields[2]);
	      rel.r_info = ELF32_R_INFO (htab->root.hgot->indx, R_SH_DIR32);
	      rel.r_addend = 8;
	      bfd_elf32_swap_reloca_out (output_bfd, &rel, loc);
	      loc += sizeof (Elf32_External_Rela);

	      /* Fix up the remaining .rela.plt.unloaded relocations.
		 They may have the wrong symbol index for _G_O_T_ or
		 _P_L_T_ depending on the order in which symbols were
		 output.  */
	      while (loc < htab->srelplt2->contents + htab->srelplt2->size)
		{
		  /* The PLT entry's pointer to the .got.plt slot.  */
		  bfd_elf32_swap_reloc_in (output_bfd, loc, &rel);
		  rel.r_info = ELF32_R_INFO (htab->root.hgot->indx,
					     R_SH_DIR32);
		  bfd_elf32_swap_reloc_out (output_bfd, &rel, loc);
		  loc += sizeof (Elf32_External_Rela);

		  /* The .got.plt slot's pointer to .plt.  */
		  bfd_elf32_swap_reloc_in (output_bfd, loc, &rel);
		  rel.r_info = ELF32_R_INFO (htab->root.hplt->indx,
					     R_SH_DIR32);
		  bfd_elf32_swap_reloc_out (output_bfd, &rel, loc);
		  loc += sizeof (Elf32_External_Rela);
		}
	    }

	  /* UnixWare sets the entsize of .plt to 4, although that doesn't
	     really seem like the right value.  */
	  elf_section_data (splt->output_section)->this_hdr.sh_entsize = 4;
	}
    }

  /* Fill in the first three entries in the global offset table.  */
  if (sgotplt && sgotplt->size > 0 && !htab->fdpic_p)
    {
      if (sdyn == NULL)
	bfd_put_32 (output_bfd, (bfd_vma) 0, sgotplt->contents);
      else
	bfd_put_32 (output_bfd,
		    sdyn->output_section->vma + sdyn->output_offset,
		    sgotplt->contents);
      bfd_put_32 (output_bfd, (bfd_vma) 0, sgotplt->contents + 4);
      bfd_put_32 (output_bfd, (bfd_vma) 0, sgotplt->contents + 8);
    }

  if (sgotplt && sgotplt->size > 0)
    elf_section_data (sgotplt->output_section)->this_hdr.sh_entsize = 4;

  /* At the very end of the .rofixup section is a pointer to the GOT.  */
  if (htab->fdpic_p && htab->srofixup != NULL)
    {
      struct elf_link_hash_entry *hgot = htab->root.hgot;
      bfd_vma got_value = hgot->root.u.def.value
	+ hgot->root.u.def.section->output_section->vma
	+ hgot->root.u.def.section->output_offset;

      sh_elf_add_rofixup (output_bfd, htab->srofixup, got_value);

      /* Make sure we allocated and generated the same number of fixups.  */
      BFD_ASSERT (htab->srofixup->reloc_count * 4 == htab->srofixup->size);
    }

  if (htab->srelfuncdesc)
    BFD_ASSERT (htab->srelfuncdesc->reloc_count * sizeof (Elf32_External_Rela)
		== htab->srelfuncdesc->size);

  if (htab->root.srelgot)
    BFD_ASSERT (htab->root.srelgot->reloc_count * sizeof (Elf32_External_Rela)
		== htab->root.srelgot->size);

  return TRUE;
}

static enum elf_reloc_type_class
sh_elf_reloc_type_class (const struct bfd_link_info *info ATTRIBUTE_UNUSED,
			 const asection *rel_sec ATTRIBUTE_UNUSED,
			 const Elf_Internal_Rela *rela)
{
  switch ((int) ELF32_R_TYPE (rela->r_info))
    {
    case R_SH_RELATIVE:
      return reloc_class_relative;
    case R_SH_JMP_SLOT:
      return reloc_class_plt;
    case R_SH_COPY:
      return reloc_class_copy;
    default:
      return reloc_class_normal;
    }
}

#if !defined SH_TARGET_ALREADY_DEFINED
/* Support for Linux core dump NOTE sections.  */

static bfd_boolean
elf32_shlin_grok_prstatus (bfd *abfd, Elf_Internal_Note *note)
{
  int offset;
  unsigned int size;

  switch (note->descsz)
    {
      default:
	return FALSE;

      case 168:		/* Linux/SH */
	/* pr_cursig */
	elf_tdata (abfd)->core->signal = bfd_get_16 (abfd, note->descdata + 12);

	/* pr_pid */
	elf_tdata (abfd)->core->lwpid = bfd_get_32 (abfd, note->descdata + 24);

	/* pr_reg */
	offset = 72;
	size = 92;

	break;
    }

  /* Make a ".reg/999" section.  */
  return _bfd_elfcore_make_pseudosection (abfd, ".reg",
					  size, note->descpos + offset);
}

static bfd_boolean
elf32_shlin_grok_psinfo (bfd *abfd, Elf_Internal_Note *note)
{
  switch (note->descsz)
    {
      default:
	return FALSE;

      case 124:		/* Linux/SH elf_prpsinfo */
	elf_tdata (abfd)->core->program
	 = _bfd_elfcore_strndup (abfd, note->descdata + 28, 16);
	elf_tdata (abfd)->core->command
	 = _bfd_elfcore_strndup (abfd, note->descdata + 44, 80);
    }

  /* Note that for some reason, a spurious space is tacked
     onto the end of the args in some (at least one anyway)
     implementations, so strip it off if it exists.  */

  {
    char *command = elf_tdata (abfd)->core->command;
    int n = strlen (command);

    if (0 < n && command[n - 1] == ' ')
      command[n - 1] = '\0';
  }

  return TRUE;
}
#endif /* not SH_TARGET_ALREADY_DEFINED */


/* Return address for Ith PLT stub in section PLT, for relocation REL
   or (bfd_vma) -1 if it should not be included.  */

static bfd_vma
sh_elf_plt_sym_val (bfd_vma i, const asection *plt,
		    const arelent *rel ATTRIBUTE_UNUSED)
{
  const struct elf_sh_plt_info *plt_info;

  plt_info = get_plt_info (plt->owner, (plt->owner->flags & DYNAMIC) != 0);
  return plt->vma + get_plt_offset (plt_info, i);
}

/* Decide whether to attempt to turn absptr or lsda encodings in
   shared libraries into pcrel within the given input section.  */

static bfd_boolean
sh_elf_use_relative_eh_frame (bfd *input_bfd ATTRIBUTE_UNUSED,
			      struct bfd_link_info *info,
			      asection *eh_frame_section ATTRIBUTE_UNUSED)
{
  struct elf_sh_link_hash_table *htab = sh_elf_hash_table (info);

  /* We can't use PC-relative encodings in FDPIC binaries, in general.  */
  if (htab->fdpic_p)
    return FALSE;

  return TRUE;
}

/* Adjust the contents of an eh_frame_hdr section before they're output.  */

static bfd_byte
sh_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_sh_link_hash_table *htab = sh_elf_hash_table (info);
  struct elf_link_hash_entry *h;

  if (!htab->fdpic_p)
    return _bfd_elf_encode_eh_address (abfd, info, osec, offset, loc_sec,
				       loc_offset, encoded);

  h = htab->root.hgot;
  BFD_ASSERT (h && h->root.type == bfd_link_hash_defined);

  if (! h || (sh_elf_osec_to_segment (abfd, osec)
	      == sh_elf_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 (sh_elf_osec_to_segment (abfd, osec)
	      == (sh_elf_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;
}

#if !defined SH_TARGET_ALREADY_DEFINED
#define TARGET_BIG_SYM		sh_elf32_vec
#define TARGET_BIG_NAME		"elf32-sh"
#define TARGET_LITTLE_SYM	sh_elf32_le_vec
#define TARGET_LITTLE_NAME	"elf32-shl"
#endif

#define ELF_ARCH		bfd_arch_sh
#define ELF_TARGET_ID		SH_ELF_DATA
#define ELF_MACHINE_CODE	EM_SH
#ifdef __QNXTARGET__
#define ELF_MAXPAGESIZE		0x1000
#else
#define ELF_MAXPAGESIZE		0x80
#endif

#define elf_symbol_leading_char '_'

#define bfd_elf32_bfd_reloc_type_lookup	sh_elf_reloc_type_lookup
#define bfd_elf32_bfd_reloc_name_lookup \
					sh_elf_reloc_name_lookup
#define elf_info_to_howto		sh_elf_info_to_howto
#define bfd_elf32_bfd_relax_section	sh_elf_relax_section
#define elf_backend_relocate_section	sh_elf_relocate_section
#define bfd_elf32_bfd_get_relocated_section_contents \
					sh_elf_get_relocated_section_contents
#define bfd_elf32_mkobject		sh_elf_mkobject
#define elf_backend_object_p		sh_elf_object_p
#define bfd_elf32_bfd_copy_private_bfd_data \
					sh_elf_copy_private_data
#define bfd_elf32_bfd_merge_private_bfd_data \
					sh_elf_merge_private_data

#define elf_backend_gc_mark_hook	sh_elf_gc_mark_hook
#define elf_backend_check_relocs	sh_elf_check_relocs
#define elf_backend_copy_indirect_symbol \
					sh_elf_copy_indirect_symbol
#define elf_backend_create_dynamic_sections \
					sh_elf_create_dynamic_sections
#define bfd_elf32_bfd_link_hash_table_create \
					sh_elf_link_hash_table_create
#define elf_backend_adjust_dynamic_symbol \
					sh_elf_adjust_dynamic_symbol
#define elf_backend_always_size_sections \
					sh_elf_always_size_sections
#define elf_backend_size_dynamic_sections \
					sh_elf_size_dynamic_sections
#define elf_backend_omit_section_dynsym	sh_elf_omit_section_dynsym
#define elf_backend_finish_dynamic_symbol \
					sh_elf_finish_dynamic_symbol
#define elf_backend_finish_dynamic_sections \
					sh_elf_finish_dynamic_sections
#define elf_backend_reloc_type_class	sh_elf_reloc_type_class
#define elf_backend_plt_sym_val		sh_elf_plt_sym_val
#define elf_backend_can_make_relative_eh_frame \
					sh_elf_use_relative_eh_frame
#define elf_backend_can_make_lsda_relative_eh_frame \
					sh_elf_use_relative_eh_frame
#define elf_backend_encode_eh_address \
					sh_elf_encode_eh_address

#define elf_backend_stack_align		8
#define elf_backend_can_gc_sections	1
#define elf_backend_can_refcount	1
#define elf_backend_want_got_plt	1
#define elf_backend_plt_readonly	1
#define elf_backend_want_plt_sym	0
#define elf_backend_got_header_size	12
#define elf_backend_dtrel_excludes_plt	1

#define elf_backend_linux_prpsinfo32_ugid16	TRUE

#if !defined INCLUDE_SHMEDIA && !defined SH_TARGET_ALREADY_DEFINED

#include "elf32-target.h"

/* NetBSD support.  */
#undef	TARGET_BIG_SYM
#define	TARGET_BIG_SYM			sh_elf32_nbsd_vec
#undef	TARGET_BIG_NAME
#define	TARGET_BIG_NAME			"elf32-sh-nbsd"
#undef	TARGET_LITTLE_SYM
#define	TARGET_LITTLE_SYM		sh_elf32_nbsd_le_vec
#undef	TARGET_LITTLE_NAME
#define	TARGET_LITTLE_NAME		"elf32-shl-nbsd"
#undef	ELF_MAXPAGESIZE
#define	ELF_MAXPAGESIZE			0x10000
#undef	ELF_COMMONPAGESIZE
#undef	elf_symbol_leading_char
#define	elf_symbol_leading_char		0
#undef	elf32_bed
#define	elf32_bed			elf32_sh_nbsd_bed

#include "elf32-target.h"


/* Linux support.  */
#undef	TARGET_BIG_SYM
#define	TARGET_BIG_SYM			sh_elf32_linux_be_vec
#undef	TARGET_BIG_NAME
#define	TARGET_BIG_NAME			"elf32-shbig-linux"
#undef	TARGET_LITTLE_SYM
#define	TARGET_LITTLE_SYM		sh_elf32_linux_vec
#undef	TARGET_LITTLE_NAME
#define	TARGET_LITTLE_NAME		"elf32-sh-linux"
#undef	ELF_COMMONPAGESIZE
#define	ELF_COMMONPAGESIZE		0x1000

#undef	elf_backend_grok_prstatus
#define	elf_backend_grok_prstatus	elf32_shlin_grok_prstatus
#undef	elf_backend_grok_psinfo
#define	elf_backend_grok_psinfo		elf32_shlin_grok_psinfo
#undef	elf32_bed
#define	elf32_bed			elf32_sh_lin_bed

#include "elf32-target.h"


/* FDPIC support.  */
#undef	TARGET_BIG_SYM
#define	TARGET_BIG_SYM			sh_elf32_fdpic_be_vec
#undef	TARGET_BIG_NAME
#define	TARGET_BIG_NAME			"elf32-shbig-fdpic"
#undef	TARGET_LITTLE_SYM
#define	TARGET_LITTLE_SYM		sh_elf32_fdpic_le_vec
#undef	TARGET_LITTLE_NAME
#define	TARGET_LITTLE_NAME		"elf32-sh-fdpic"

#undef	elf32_bed
#define	elf32_bed			elf32_sh_fd_bed

#include "elf32-target.h"

#undef elf_backend_modify_program_headers

/* VxWorks support.  */
#undef	TARGET_BIG_SYM
#define	TARGET_BIG_SYM			sh_elf32_vxworks_vec
#undef	TARGET_BIG_NAME
#define	TARGET_BIG_NAME			"elf32-sh-vxworks"
#undef	TARGET_LITTLE_SYM
#define	TARGET_LITTLE_SYM		sh_elf32_vxworks_le_vec
#undef	TARGET_LITTLE_NAME
#define	TARGET_LITTLE_NAME		"elf32-shl-vxworks"
#undef	elf32_bed
#define	elf32_bed			elf32_sh_vxworks_bed

#undef	elf_backend_want_plt_sym
#define	elf_backend_want_plt_sym	1
#undef	elf_symbol_leading_char
#define	elf_symbol_leading_char		'_'
#define	elf_backend_want_got_underscore 1
#undef	elf_backend_grok_prstatus
#undef	elf_backend_grok_psinfo
#undef	elf_backend_add_symbol_hook
#define	elf_backend_add_symbol_hook	elf_vxworks_add_symbol_hook
#undef	elf_backend_link_output_symbol_hook
#define	elf_backend_link_output_symbol_hook \
					elf_vxworks_link_output_symbol_hook
#undef	elf_backend_emit_relocs
#define	elf_backend_emit_relocs		elf_vxworks_emit_relocs
#undef	elf_backend_final_write_processing
#define	elf_backend_final_write_processing \
					elf_vxworks_final_write_processing
#undef	ELF_MAXPAGESIZE
#define	ELF_MAXPAGESIZE			0x1000
#undef	ELF_COMMONPAGESIZE

#include "elf32-target.h"

#endif /* neither INCLUDE_SHMEDIA nor SH_TARGET_ALREADY_DEFINED */
