/* Xtensa-specific support for 32-bit ELF.
   Copyright 2003, 2004, 2005 Free Software Foundation, Inc.

   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 2 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 "bfd.h"
#include "sysdep.h"

#ifdef ANSI_PROTOTYPES
#include <stdarg.h>
#else
#include <varargs.h>
#endif
#include <strings.h>

#include "bfdlink.h"
#include "libbfd.h"
#include "elf-bfd.h"
#include "elf/xtensa.h"
#include "xtensa-isa.h"
#include "xtensa-config.h"

#define XTENSA_NO_NOP_REMOVAL 0

/* Local helper functions.  */

static bfd_boolean add_extra_plt_sections (bfd *, int);
static char *build_encoding_error_message (xtensa_opcode, bfd_vma);
static bfd_reloc_status_type bfd_elf_xtensa_reloc
  (bfd *, arelent *, asymbol *, void *, asection *, bfd *, char **);
static bfd_boolean do_fix_for_relocatable_link
  (Elf_Internal_Rela *, bfd *, asection *, bfd_byte *);
static void do_fix_for_final_link
  (Elf_Internal_Rela *, bfd *, asection *, bfd_byte *, bfd_vma *);

/* Local functions to handle Xtensa configurability.  */

static bfd_boolean is_indirect_call_opcode (xtensa_opcode);
static bfd_boolean is_direct_call_opcode (xtensa_opcode);
static bfd_boolean is_windowed_call_opcode (xtensa_opcode);
static xtensa_opcode get_const16_opcode (void);
static xtensa_opcode get_l32r_opcode (void);
static bfd_vma l32r_offset (bfd_vma, bfd_vma);
static int get_relocation_opnd (xtensa_opcode, int);
static int get_relocation_slot (int);
static xtensa_opcode get_relocation_opcode
  (bfd *, asection *, bfd_byte *, Elf_Internal_Rela *);
static bfd_boolean is_l32r_relocation
  (bfd *, asection *, bfd_byte *, Elf_Internal_Rela *);
static bfd_boolean is_alt_relocation (int);
static bfd_boolean is_operand_relocation (int);
static bfd_size_type insn_decode_len
  (bfd_byte *, bfd_size_type, bfd_size_type);
static xtensa_opcode insn_decode_opcode
  (bfd_byte *, bfd_size_type, bfd_size_type, int);
static bfd_boolean check_branch_target_aligned
  (bfd_byte *, bfd_size_type, bfd_vma, bfd_vma);
static bfd_boolean check_loop_aligned
  (bfd_byte *, bfd_size_type, bfd_vma, bfd_vma);
static bfd_boolean check_branch_target_aligned_address (bfd_vma, int);
static bfd_size_type get_asm_simplify_size
  (bfd_byte *, bfd_size_type, bfd_size_type);

/* Functions for link-time code simplifications.  */

static bfd_reloc_status_type elf_xtensa_do_asm_simplify
  (bfd_byte *, bfd_vma, bfd_vma, char **);
static bfd_reloc_status_type contract_asm_expansion
  (bfd_byte *, bfd_vma, Elf_Internal_Rela *, char **);
static xtensa_opcode swap_callx_for_call_opcode (xtensa_opcode);
static xtensa_opcode get_expanded_call_opcode (bfd_byte *, int, bfd_boolean *);

/* Access to internal relocations, section contents and symbols.  */

static Elf_Internal_Rela *retrieve_internal_relocs
  (bfd *, asection *, bfd_boolean);
static void pin_internal_relocs (asection *, Elf_Internal_Rela *);
static void release_internal_relocs (asection *, Elf_Internal_Rela *);
static bfd_byte *retrieve_contents (bfd *, asection *, bfd_boolean);
static void pin_contents (asection *, bfd_byte *);
static void release_contents (asection *, bfd_byte *);
static Elf_Internal_Sym *retrieve_local_syms (bfd *);

/* Miscellaneous utility functions.  */

static asection *elf_xtensa_get_plt_section (bfd *, int);
static asection *elf_xtensa_get_gotplt_section (bfd *, int);
static asection *get_elf_r_symndx_section (bfd *, unsigned long);
static struct elf_link_hash_entry *get_elf_r_symndx_hash_entry
  (bfd *, unsigned long);
static bfd_vma get_elf_r_symndx_offset (bfd *, unsigned long);
static bfd_boolean is_reloc_sym_weak (bfd *, Elf_Internal_Rela *);
static bfd_boolean pcrel_reloc_fits (xtensa_opcode, int, bfd_vma, bfd_vma);
static bfd_boolean xtensa_is_property_section (asection *);
static bfd_boolean xtensa_is_littable_section (asection *);
static int internal_reloc_compare (const void *, const void *);
static int internal_reloc_matches (const void *, const void *);
extern char *xtensa_get_property_section_name (asection *, const char *);
static flagword xtensa_get_property_predef_flags (asection *);

/* Other functions called directly by the linker.  */

typedef void (*deps_callback_t)
  (asection *, bfd_vma, asection *, bfd_vma, void *);
extern bfd_boolean xtensa_callback_required_dependence
  (bfd *, asection *, struct bfd_link_info *, deps_callback_t, void *);


/* Globally visible flag for choosing size optimization of NOP removal
   instead of branch-target-aware minimization for NOP removal.
   When nonzero, narrow all instructions and remove all NOPs possible
   around longcall expansions.  */

int elf32xtensa_size_opt;


/* The "new_section_hook" is used to set up a per-section
   "xtensa_relax_info" data structure with additional information used
   during relaxation.  */

typedef struct xtensa_relax_info_struct xtensa_relax_info;


/* Total count of PLT relocations seen during check_relocs.
   The actual PLT code must be split into multiple sections and all
   the sections have to be created before size_dynamic_sections,
   where we figure out the exact number of PLT entries that will be
   needed.  It is OK if this count is an overestimate, e.g., some
   relocations may be removed by GC.  */

static int plt_reloc_count = 0;


/* The GNU tools do not easily allow extending interfaces to pass around
   the pointer to the Xtensa ISA information, so instead we add a global
   variable here (in BFD) that can be used by any of the tools that need
   this information. */

xtensa_isa xtensa_default_isa;


/* When this is true, relocations may have been modified to refer to
   symbols from other input files.  The per-section list of "fix"
   records needs to be checked when resolving relocations.  */

static bfd_boolean relaxing_section = FALSE;

/* When this is true, during final links, literals that cannot be
   coalesced and their relocations may be moved to other sections.  */

int elf32xtensa_no_literal_movement = 1;


static reloc_howto_type elf_howto_table[] =
{
  HOWTO (R_XTENSA_NONE, 0, 0, 0, FALSE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_NONE",
	 FALSE, 0x00000000, 0x00000000, FALSE),
  HOWTO (R_XTENSA_32, 0, 2, 32, FALSE, 0, complain_overflow_bitfield,
	 bfd_elf_xtensa_reloc, "R_XTENSA_32",
	 TRUE, 0xffffffff, 0xffffffff, FALSE),
  /* Replace a 32-bit value with a value from the runtime linker (only
     used by linker-generated stub functions).  The r_addend value is
     special: 1 means to substitute a pointer to the runtime linker's
     dynamic resolver function; 2 means to substitute the link map for
     the shared object.  */
  HOWTO (R_XTENSA_RTLD, 0, 2, 32, FALSE, 0, complain_overflow_dont,
	 NULL, "R_XTENSA_RTLD",
	 FALSE, 0x00000000, 0x00000000, FALSE),
  HOWTO (R_XTENSA_GLOB_DAT, 0, 2, 32, FALSE, 0, complain_overflow_bitfield,
	 bfd_elf_generic_reloc, "R_XTENSA_GLOB_DAT",
	 FALSE, 0xffffffff, 0xffffffff, FALSE),
  HOWTO (R_XTENSA_JMP_SLOT, 0, 2, 32, FALSE, 0, complain_overflow_bitfield,
	 bfd_elf_generic_reloc, "R_XTENSA_JMP_SLOT",
	 FALSE, 0xffffffff, 0xffffffff, FALSE),
  HOWTO (R_XTENSA_RELATIVE, 0, 2, 32, FALSE, 0, complain_overflow_bitfield,
	 bfd_elf_generic_reloc, "R_XTENSA_RELATIVE",
	 FALSE, 0xffffffff, 0xffffffff, FALSE),
  HOWTO (R_XTENSA_PLT, 0, 2, 32, FALSE, 0, complain_overflow_bitfield,
	 bfd_elf_xtensa_reloc, "R_XTENSA_PLT",
	 FALSE, 0xffffffff, 0xffffffff, FALSE),
  EMPTY_HOWTO (7),
  HOWTO (R_XTENSA_OP0, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_OP0",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_OP1, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_OP1",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_OP2, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_OP2",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  /* Assembly auto-expansion.  */
  HOWTO (R_XTENSA_ASM_EXPAND, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_ASM_EXPAND",
	 FALSE, 0x00000000, 0x00000000, FALSE),
  /* Relax assembly auto-expansion.  */
  HOWTO (R_XTENSA_ASM_SIMPLIFY, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_ASM_SIMPLIFY",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  EMPTY_HOWTO (13),
  EMPTY_HOWTO (14),
  /* GNU extension to record C++ vtable hierarchy.  */
  HOWTO (R_XTENSA_GNU_VTINHERIT, 0, 2, 0, FALSE, 0, complain_overflow_dont,
         NULL, "R_XTENSA_GNU_VTINHERIT",
	 FALSE, 0x00000000, 0x00000000, FALSE),
  /* GNU extension to record C++ vtable member usage.  */
  HOWTO (R_XTENSA_GNU_VTENTRY, 0, 2, 0, FALSE, 0, complain_overflow_dont,
         _bfd_elf_rel_vtable_reloc_fn, "R_XTENSA_GNU_VTENTRY",
	 FALSE, 0x00000000, 0x00000000, FALSE),

  /* Relocations for supporting difference of symbols.  */
  HOWTO (R_XTENSA_DIFF8, 0, 0, 8, FALSE, 0, complain_overflow_bitfield,
	 bfd_elf_xtensa_reloc, "R_XTENSA_DIFF8",
	 FALSE, 0xffffffff, 0xffffffff, FALSE),
  HOWTO (R_XTENSA_DIFF16, 0, 1, 16, FALSE, 0, complain_overflow_bitfield,
	 bfd_elf_xtensa_reloc, "R_XTENSA_DIFF16",
	 FALSE, 0xffffffff, 0xffffffff, FALSE),
  HOWTO (R_XTENSA_DIFF32, 0, 2, 32, FALSE, 0, complain_overflow_bitfield,
	 bfd_elf_xtensa_reloc, "R_XTENSA_DIFF32",
	 FALSE, 0xffffffff, 0xffffffff, FALSE),

  /* General immediate operand relocations.  */
  HOWTO (R_XTENSA_SLOT0_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT0_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT1_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT1_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT2_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT2_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT3_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT3_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT4_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT4_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT5_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT5_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT6_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT6_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT7_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT7_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT8_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT8_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT9_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT9_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT10_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT10_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT11_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT11_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT12_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT12_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT13_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT13_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT14_OP, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT14_OP",
	 FALSE, 0x00000000, 0x00000000, TRUE),

  /* "Alternate" relocations.  The meaning of these is opcode-specific.  */
  HOWTO (R_XTENSA_SLOT0_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT0_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT1_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT1_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT2_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT2_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT3_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT3_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT4_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT4_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT5_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT5_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT6_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT6_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT7_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT7_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT8_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT8_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT9_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT9_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT10_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT10_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT11_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT11_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT12_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT12_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT13_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT13_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE),
  HOWTO (R_XTENSA_SLOT14_ALT, 0, 0, 0, TRUE, 0, complain_overflow_dont,
	 bfd_elf_xtensa_reloc, "R_XTENSA_SLOT14_ALT",
	 FALSE, 0x00000000, 0x00000000, TRUE)
};

#if DEBUG_GEN_RELOC
#define TRACE(str) \
  fprintf (stderr, "Xtensa bfd reloc lookup %d (%s)\n", code, str)
#else
#define TRACE(str)
#endif

static reloc_howto_type *
elf_xtensa_reloc_type_lookup (bfd *abfd ATTRIBUTE_UNUSED,
			      bfd_reloc_code_real_type code)
{
  switch (code)
    {
    case BFD_RELOC_NONE:
      TRACE ("BFD_RELOC_NONE");
      return &elf_howto_table[(unsigned) R_XTENSA_NONE ];

    case BFD_RELOC_32:
      TRACE ("BFD_RELOC_32");
      return &elf_howto_table[(unsigned) R_XTENSA_32 ];

    case BFD_RELOC_XTENSA_DIFF8:
      TRACE ("BFD_RELOC_XTENSA_DIFF8");
      return &elf_howto_table[(unsigned) R_XTENSA_DIFF8 ];

    case BFD_RELOC_XTENSA_DIFF16:
      TRACE ("BFD_RELOC_XTENSA_DIFF16");
      return &elf_howto_table[(unsigned) R_XTENSA_DIFF16 ];

    case BFD_RELOC_XTENSA_DIFF32:
      TRACE ("BFD_RELOC_XTENSA_DIFF32");
      return &elf_howto_table[(unsigned) R_XTENSA_DIFF32 ];

    case BFD_RELOC_XTENSA_RTLD:
      TRACE ("BFD_RELOC_XTENSA_RTLD");
      return &elf_howto_table[(unsigned) R_XTENSA_RTLD ];

    case BFD_RELOC_XTENSA_GLOB_DAT:
      TRACE ("BFD_RELOC_XTENSA_GLOB_DAT");
      return &elf_howto_table[(unsigned) R_XTENSA_GLOB_DAT ];

    case BFD_RELOC_XTENSA_JMP_SLOT:
      TRACE ("BFD_RELOC_XTENSA_JMP_SLOT");
      return &elf_howto_table[(unsigned) R_XTENSA_JMP_SLOT ];

    case BFD_RELOC_XTENSA_RELATIVE:
      TRACE ("BFD_RELOC_XTENSA_RELATIVE");
      return &elf_howto_table[(unsigned) R_XTENSA_RELATIVE ];

    case BFD_RELOC_XTENSA_PLT:
      TRACE ("BFD_RELOC_XTENSA_PLT");
      return &elf_howto_table[(unsigned) R_XTENSA_PLT ];

    case BFD_RELOC_XTENSA_OP0:
      TRACE ("BFD_RELOC_XTENSA_OP0");
      return &elf_howto_table[(unsigned) R_XTENSA_OP0 ];

    case BFD_RELOC_XTENSA_OP1:
      TRACE ("BFD_RELOC_XTENSA_OP1");
      return &elf_howto_table[(unsigned) R_XTENSA_OP1 ];

    case BFD_RELOC_XTENSA_OP2:
      TRACE ("BFD_RELOC_XTENSA_OP2");
      return &elf_howto_table[(unsigned) R_XTENSA_OP2 ];

    case BFD_RELOC_XTENSA_ASM_EXPAND:
      TRACE ("BFD_RELOC_XTENSA_ASM_EXPAND");
      return &elf_howto_table[(unsigned) R_XTENSA_ASM_EXPAND ];

    case BFD_RELOC_XTENSA_ASM_SIMPLIFY:
      TRACE ("BFD_RELOC_XTENSA_ASM_SIMPLIFY");
      return &elf_howto_table[(unsigned) R_XTENSA_ASM_SIMPLIFY ];

    case BFD_RELOC_VTABLE_INHERIT:
      TRACE ("BFD_RELOC_VTABLE_INHERIT");
      return &elf_howto_table[(unsigned) R_XTENSA_GNU_VTINHERIT ];

    case BFD_RELOC_VTABLE_ENTRY:
      TRACE ("BFD_RELOC_VTABLE_ENTRY");
      return &elf_howto_table[(unsigned) R_XTENSA_GNU_VTENTRY ];

    default:
      if (code >= BFD_RELOC_XTENSA_SLOT0_OP
	  && code <= BFD_RELOC_XTENSA_SLOT14_OP)
	{
	  unsigned n = (R_XTENSA_SLOT0_OP +
			(code - BFD_RELOC_XTENSA_SLOT0_OP));
	  return &elf_howto_table[n];
	}

      if (code >= BFD_RELOC_XTENSA_SLOT0_ALT
	  && code <= BFD_RELOC_XTENSA_SLOT14_ALT)
	{
	  unsigned n = (R_XTENSA_SLOT0_ALT +
			(code - BFD_RELOC_XTENSA_SLOT0_ALT));
	  return &elf_howto_table[n];
	}

      break;
    }

  TRACE ("Unknown");
  return NULL;
}


/* Given an ELF "rela" relocation, find the corresponding howto and record
   it in the BFD internal arelent representation of the relocation.  */

static void
elf_xtensa_info_to_howto_rela (bfd *abfd ATTRIBUTE_UNUSED,
			       arelent *cache_ptr,
			       Elf_Internal_Rela *dst)
{
  unsigned int r_type = ELF32_R_TYPE (dst->r_info);

  BFD_ASSERT (r_type < (unsigned int) R_XTENSA_max);
  cache_ptr->howto = &elf_howto_table[r_type];
}


/* Functions for the Xtensa ELF linker.  */

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

#define ELF_DYNAMIC_INTERPRETER "/lib/ld.so"

/* The size in bytes of an entry in the procedure linkage table.
   (This does _not_ include the space for the literals associated with
   the PLT entry.) */

#define PLT_ENTRY_SIZE 16

/* For _really_ large PLTs, we may need to alternate between literals
   and code to keep the literals within the 256K range of the L32R
   instructions in the code.  It's unlikely that anyone would ever need
   such a big PLT, but an arbitrary limit on the PLT size would be bad.
   Thus, we split the PLT into chunks.  Since there's very little
   overhead (2 extra literals) for each chunk, the chunk size is kept
   small so that the code for handling multiple chunks get used and
   tested regularly.  With 254 entries, there are 1K of literals for
   each chunk, and that seems like a nice round number.  */

#define PLT_ENTRIES_PER_CHUNK 254

/* PLT entries are actually used as stub functions for lazy symbol
   resolution.  Once the symbol is resolved, the stub function is never
   invoked.  Note: the 32-byte frame size used here cannot be changed
   without a corresponding change in the runtime linker.  */

static const bfd_byte elf_xtensa_be_plt_entry[PLT_ENTRY_SIZE] =
{
  0x6c, 0x10, 0x04,	/* entry sp, 32 */
  0x18, 0x00, 0x00,	/* l32r  a8, [got entry for rtld's resolver] */
  0x1a, 0x00, 0x00,	/* l32r  a10, [got entry for rtld's link map] */
  0x1b, 0x00, 0x00,	/* l32r  a11, [literal for reloc index] */
  0x0a, 0x80, 0x00,	/* jx    a8 */
  0			/* unused */
};

static const bfd_byte elf_xtensa_le_plt_entry[PLT_ENTRY_SIZE] =
{
  0x36, 0x41, 0x00,	/* entry sp, 32 */
  0x81, 0x00, 0x00,	/* l32r  a8, [got entry for rtld's resolver] */
  0xa1, 0x00, 0x00,	/* l32r  a10, [got entry for rtld's link map] */
  0xb1, 0x00, 0x00,	/* l32r  a11, [literal for reloc index] */
  0xa0, 0x08, 0x00,	/* jx    a8 */
  0			/* unused */
};


static inline bfd_boolean
xtensa_elf_dynamic_symbol_p (struct elf_link_hash_entry *h,
			     struct bfd_link_info *info)
{
  /* Check if we should do dynamic things to this symbol.  The
     "ignore_protected" argument need not be set, because Xtensa code
     does not require special handling of STV_PROTECTED to make function
     pointer comparisons work properly.  The PLT addresses are never
     used for function pointers.  */

  return _bfd_elf_dynamic_symbol_p (h, info, 0);
}


static int
property_table_compare (const void *ap, const void *bp)
{
  const property_table_entry *a = (const property_table_entry *) ap;
  const property_table_entry *b = (const property_table_entry *) bp;

  if (a->address == b->address)
    {
      if (a->size != b->size)
	return (a->size - b->size);

      if ((a->flags & XTENSA_PROP_ALIGN) != (b->flags & XTENSA_PROP_ALIGN))
	return ((b->flags & XTENSA_PROP_ALIGN)
		- (a->flags & XTENSA_PROP_ALIGN));

      if ((a->flags & XTENSA_PROP_ALIGN)
	  && (GET_XTENSA_PROP_ALIGNMENT (a->flags)
	      != GET_XTENSA_PROP_ALIGNMENT (b->flags)))
	return (GET_XTENSA_PROP_ALIGNMENT (a->flags)
		- GET_XTENSA_PROP_ALIGNMENT (b->flags));
      
      if ((a->flags & XTENSA_PROP_UNREACHABLE)
	  != (b->flags & XTENSA_PROP_UNREACHABLE))
	return ((b->flags & XTENSA_PROP_UNREACHABLE)
		- (a->flags & XTENSA_PROP_UNREACHABLE));

      return (a->flags - b->flags);
    }

  return (a->address - b->address);
}


static int
property_table_matches (const void *ap, const void *bp)
{
  const property_table_entry *a = (const property_table_entry *) ap;
  const property_table_entry *b = (const property_table_entry *) bp;

  /* Check if one entry overlaps with the other.  */
  if ((b->address >= a->address && b->address < (a->address + a->size))
      || (a->address >= b->address && a->address < (b->address + b->size)))
    return 0;

  return (a->address - b->address);
}


/* Get the literal table or property table entries for the given
   section.  Sets TABLE_P and returns the number of entries.  On
   error, returns a negative value.  */

static int
xtensa_read_table_entries (bfd *abfd,
			   asection *section,
			   property_table_entry **table_p,
			   const char *sec_name,
			   bfd_boolean output_addr)
{
  asection *table_section;
  char *table_section_name;
  bfd_size_type table_size = 0;
  bfd_byte *table_data;
  property_table_entry *blocks;
  int blk, block_count;
  bfd_size_type num_records;
  Elf_Internal_Rela *internal_relocs;
  bfd_vma section_addr;
  flagword predef_flags;
  bfd_size_type table_entry_size;

  if (!section
      || !(section->flags & SEC_ALLOC)
      || (section->flags & SEC_DEBUGGING))
    {
      *table_p = NULL;
      return 0;
    }

  table_section_name = xtensa_get_property_section_name (section, sec_name);
  table_section = bfd_get_section_by_name (abfd, table_section_name);
  free (table_section_name);
  if (table_section)
    table_size = table_section->size;

  if (table_size == 0) 
    {
      *table_p = NULL;
      return 0;
    }

  predef_flags = xtensa_get_property_predef_flags (table_section);
  table_entry_size = 12;
  if (predef_flags)
    table_entry_size -= 4;

  num_records = table_size / table_entry_size;
  table_data = retrieve_contents (abfd, table_section, TRUE);
  blocks = (property_table_entry *)
    bfd_malloc (num_records * sizeof (property_table_entry));
  block_count = 0;

  if (output_addr)
    section_addr = section->output_section->vma + section->output_offset;
  else
    section_addr = section->vma;

  /* If the file has not yet been relocated, process the relocations
     and sort out the table entries that apply to the specified section.  */
  internal_relocs = retrieve_internal_relocs (abfd, table_section, TRUE);
  if (internal_relocs && !table_section->reloc_done)
    {
      unsigned i;

      for (i = 0; i < table_section->reloc_count; i++)
	{
	  Elf_Internal_Rela *rel = &internal_relocs[i];
	  unsigned long r_symndx;

	  if (ELF32_R_TYPE (rel->r_info) == R_XTENSA_NONE)
	    continue;

	  BFD_ASSERT (ELF32_R_TYPE (rel->r_info) == R_XTENSA_32);
	  r_symndx = ELF32_R_SYM (rel->r_info);

	  if (get_elf_r_symndx_section (abfd, r_symndx) == section)
	    {
	      bfd_vma sym_off = get_elf_r_symndx_offset (abfd, r_symndx);
	      BFD_ASSERT (sym_off == 0);
	      BFD_ASSERT (rel->r_addend == 0);
	      blocks[block_count].address =
		(section_addr + sym_off + rel->r_addend
		 + bfd_get_32 (abfd, table_data + rel->r_offset));
	      blocks[block_count].size =
		bfd_get_32 (abfd, table_data + rel->r_offset + 4);
	      if (predef_flags)
		blocks[block_count].flags = predef_flags;
	      else
		blocks[block_count].flags =
		  bfd_get_32 (abfd, table_data + rel->r_offset + 8);
	      block_count++;
	    }
	}
    }
  else
    {
      /* The file has already been relocated and the addresses are
	 already in the table.  */
      bfd_vma off;
      bfd_size_type section_limit = bfd_get_section_limit (abfd, section);

      for (off = 0; off < table_size; off += table_entry_size) 
	{
	  bfd_vma address = bfd_get_32 (abfd, table_data + off);

	  if (address >= section_addr
	      && address < section_addr + section_limit)
	    {
	      blocks[block_count].address = address;
	      blocks[block_count].size =
		bfd_get_32 (abfd, table_data + off + 4);
	      if (predef_flags)
		blocks[block_count].flags = predef_flags;
	      else
		blocks[block_count].flags =
		  bfd_get_32 (abfd, table_data + off + 8);
	      block_count++;
	    }
	}
    }

  release_contents (table_section, table_data);
  release_internal_relocs (table_section, internal_relocs);

  if (block_count > 0)
    {
      /* Now sort them into address order for easy reference.  */
      qsort (blocks, block_count, sizeof (property_table_entry),
	     property_table_compare);

      /* Check that the table contents are valid.  Problems may occur,
         for example, if an unrelocated object file is stripped.  */
      for (blk = 1; blk < block_count; blk++)
	{
	  /* The only circumstance where two entries may legitimately
	     have the same address is when one of them is a zero-size
	     placeholder to mark a place where fill can be inserted.
	     The zero-size entry should come first.  */
	  if (blocks[blk - 1].address == blocks[blk].address &&
	      blocks[blk - 1].size != 0)
	    {
	      (*_bfd_error_handler) (_("%B(%A): invalid property table"),
				     abfd, section);
	      bfd_set_error (bfd_error_bad_value);
	      free (blocks);
	      return -1;
	    }
	}
    }

  *table_p = blocks;
  return block_count;
}


static property_table_entry *
elf_xtensa_find_property_entry (property_table_entry *property_table,
				int property_table_size,
				bfd_vma addr)
{
  property_table_entry entry;
  property_table_entry *rv;

  if (property_table_size == 0)
    return NULL;

  entry.address = addr;
  entry.size = 1;
  entry.flags = 0;

  rv = bsearch (&entry, property_table, property_table_size,
		sizeof (property_table_entry), property_table_matches);
  return rv;
}


static bfd_boolean
elf_xtensa_in_literal_pool (property_table_entry *lit_table,
			    int lit_table_size,
			    bfd_vma addr)
{
  if (elf_xtensa_find_property_entry (lit_table, lit_table_size, addr))
    return TRUE;

  return FALSE;
}


/* Look through the relocs for a section during the first phase, and
   calculate needed space in the dynamic reloc sections.  */

static bfd_boolean
elf_xtensa_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;
  const Elf_Internal_Rela *rel;
  const Elf_Internal_Rela *rel_end;

  if (info->relocatable)
    return TRUE;

  symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
  sym_hashes = elf_sym_hashes (abfd);

  rel_end = relocs + sec->reloc_count;
  for (rel = relocs; rel < rel_end; rel++)
    {
      unsigned int r_type;
      unsigned long r_symndx;
      struct elf_link_hash_entry *h;

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

      if (r_symndx >= NUM_SHDR_ENTRIES (symtab_hdr))
	{
	  (*_bfd_error_handler) (_("%B: bad symbol index: %d"),
				 abfd, r_symndx);
	  return FALSE;
	}

      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)
	    h = (struct elf_link_hash_entry *) h->root.u.i.link;
	}

      switch (r_type)
	{
	case R_XTENSA_32:
	  if (h == NULL)
	    goto local_literal;

	  if ((sec->flags & SEC_ALLOC) != 0)
	    {
	      if (h->got.refcount <= 0)
		h->got.refcount = 1;
	      else
		h->got.refcount += 1;
	    }
	  break;

	case R_XTENSA_PLT:
	  /* If this relocation is against a local symbol, then it's
	     exactly the same as a normal local GOT entry.  */
	  if (h == NULL)
	    goto local_literal;

	  if ((sec->flags & SEC_ALLOC) != 0)
	    {
	      if (h->plt.refcount <= 0)
		{
		  h->needs_plt = 1;
		  h->plt.refcount = 1;
		}
	      else
		h->plt.refcount += 1;

	      /* Keep track of the total PLT relocation count even if we
		 don't yet know whether the dynamic sections will be
		 created.  */
	      plt_reloc_count += 1;

	      if (elf_hash_table (info)->dynamic_sections_created)
		{
		  if (!add_extra_plt_sections (elf_hash_table (info)->dynobj,
					       plt_reloc_count))
		    return FALSE;
		}
	    }
	  break;

	local_literal:
	  if ((sec->flags & SEC_ALLOC) != 0)
	    {
	      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);
		  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;
		}
	      local_got_refcounts[r_symndx] += 1;
	    }
	  break;

	case R_XTENSA_OP0:
	case R_XTENSA_OP1:
	case R_XTENSA_OP2:
	case R_XTENSA_SLOT0_OP:
	case R_XTENSA_SLOT1_OP:
	case R_XTENSA_SLOT2_OP:
	case R_XTENSA_SLOT3_OP:
	case R_XTENSA_SLOT4_OP:
	case R_XTENSA_SLOT5_OP:
	case R_XTENSA_SLOT6_OP:
	case R_XTENSA_SLOT7_OP:
	case R_XTENSA_SLOT8_OP:
	case R_XTENSA_SLOT9_OP:
	case R_XTENSA_SLOT10_OP:
	case R_XTENSA_SLOT11_OP:
	case R_XTENSA_SLOT12_OP:
	case R_XTENSA_SLOT13_OP:
	case R_XTENSA_SLOT14_OP:
	case R_XTENSA_SLOT0_ALT:
	case R_XTENSA_SLOT1_ALT:
	case R_XTENSA_SLOT2_ALT:
	case R_XTENSA_SLOT3_ALT:
	case R_XTENSA_SLOT4_ALT:
	case R_XTENSA_SLOT5_ALT:
	case R_XTENSA_SLOT6_ALT:
	case R_XTENSA_SLOT7_ALT:
	case R_XTENSA_SLOT8_ALT:
	case R_XTENSA_SLOT9_ALT:
	case R_XTENSA_SLOT10_ALT:
	case R_XTENSA_SLOT11_ALT:
	case R_XTENSA_SLOT12_ALT:
	case R_XTENSA_SLOT13_ALT:
	case R_XTENSA_SLOT14_ALT:
	case R_XTENSA_ASM_EXPAND:
	case R_XTENSA_ASM_SIMPLIFY:
	case R_XTENSA_DIFF8:
	case R_XTENSA_DIFF16:
	case R_XTENSA_DIFF32:
	  /* Nothing to do for these.  */
	  break;

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

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

	default:
	  break;
	}
    }

  return TRUE;
}


static void
elf_xtensa_make_sym_local (struct bfd_link_info *info,
			   struct elf_link_hash_entry *h)
{
  if (info->shared)
    {
      if (h->plt.refcount > 0)
	{
	  /* Will use RELATIVE relocs instead of JMP_SLOT relocs.  */
	  if (h->got.refcount < 0)
	    h->got.refcount = 0;
	  h->got.refcount += h->plt.refcount;
	  h->plt.refcount = 0;
	}
    }
  else
    {
      /* Don't need any dynamic relocations at all.  */
      h->plt.refcount = 0;
      h->got.refcount = 0;
    }
}


static void
elf_xtensa_hide_symbol (struct bfd_link_info *info,
			struct elf_link_hash_entry *h,
			bfd_boolean force_local)
{
  /* For a shared link, move the plt refcount to the got refcount to leave
     space for RELATIVE relocs.  */
  elf_xtensa_make_sym_local (info, h);

  _bfd_elf_link_hash_hide_symbol (info, h, force_local);
}


/* Return the section that should be marked against GC for a given
   relocation.  */

static asection *
elf_xtensa_gc_mark_hook (asection *sec,
			 struct bfd_link_info *info ATTRIBUTE_UNUSED,
			 Elf_Internal_Rela *rel,
			 struct elf_link_hash_entry *h,
			 Elf_Internal_Sym *sym)
{
  if (h)
    {
      switch (ELF32_R_TYPE (rel->r_info))
	{
	case R_XTENSA_GNU_VTINHERIT:
	case R_XTENSA_GNU_VTENTRY:
	  break;

	default:
	  switch (h->root.type)
	    {
	    case bfd_link_hash_defined:
	    case bfd_link_hash_defweak:
	      return h->root.u.def.section;

	    case bfd_link_hash_common:
	      return h->root.u.c.p->section;

	    default:
	      break;
	    }
	}
    }
  else
    return bfd_section_from_elf_index (sec->owner, sym->st_shndx);

  return NULL;
}


/* Update the GOT & PLT entry reference counts
   for the section being removed.  */

static bfd_boolean
elf_xtensa_gc_sweep_hook (bfd *abfd,
			  struct bfd_link_info *info ATTRIBUTE_UNUSED,
			  asection *sec,
			  const Elf_Internal_Rela *relocs)
{
  Elf_Internal_Shdr *symtab_hdr;
  struct elf_link_hash_entry **sym_hashes;
  bfd_signed_vma *local_got_refcounts;
  const Elf_Internal_Rela *rel, *relend;

  if ((sec->flags & SEC_ALLOC) == 0)
    return TRUE;

  symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
  sym_hashes = elf_sym_hashes (abfd);
  local_got_refcounts = elf_local_got_refcounts (abfd);

  relend = relocs + sec->reloc_count;
  for (rel = relocs; rel < relend; rel++)
    {
      unsigned long r_symndx;
      unsigned int r_type;
      struct elf_link_hash_entry *h = NULL;

      r_symndx = ELF32_R_SYM (rel->r_info);
      if (r_symndx >= symtab_hdr->sh_info)
	{
	  h = sym_hashes[r_symndx - symtab_hdr->sh_info];
	  while (h->root.type == bfd_link_hash_indirect
		 || h->root.type == bfd_link_hash_warning)
	    h = (struct elf_link_hash_entry *) h->root.u.i.link;
	}

      r_type = ELF32_R_TYPE (rel->r_info);
      switch (r_type)
	{
	case R_XTENSA_32:
	  if (h == NULL)
	    goto local_literal;
	  if (h->got.refcount > 0)
	    h->got.refcount--;
	  break;

	case R_XTENSA_PLT:
	  if (h == NULL)
	    goto local_literal;
	  if (h->plt.refcount > 0)
	    h->plt.refcount--;
	  break;

	local_literal:
	  if (local_got_refcounts[r_symndx] > 0)
	    local_got_refcounts[r_symndx] -= 1;
	  break;

	default:
	  break;
	}
    }

  return TRUE;
}


/* Create all the dynamic sections.  */

static bfd_boolean
elf_xtensa_create_dynamic_sections (bfd *dynobj, struct bfd_link_info *info)
{
  flagword flags, noalloc_flags;
  asection *s;

  /* First do all the standard stuff.  */
  if (! _bfd_elf_create_dynamic_sections (dynobj, info))
    return FALSE;

  /* Create any extra PLT sections in case check_relocs has already
     been called on all the non-dynamic input files.  */
  if (!add_extra_plt_sections (dynobj, plt_reloc_count))
    return FALSE;

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

  /* Mark the ".got.plt" section READONLY.  */
  s = bfd_get_section_by_name (dynobj, ".got.plt");
  if (s == NULL
      || ! bfd_set_section_flags (dynobj, s, flags))
    return FALSE;

  /* Create ".rela.got".  */
  s = bfd_make_section_with_flags (dynobj, ".rela.got", flags);
  if (s == NULL
      || ! bfd_set_section_alignment (dynobj, s, 2))
    return FALSE;

  /* Create ".got.loc" (literal tables for use by dynamic linker).  */
  s = bfd_make_section_with_flags (dynobj, ".got.loc", flags);
  if (s == NULL
      || ! bfd_set_section_alignment (dynobj, s, 2))
    return FALSE;

  /* Create ".xt.lit.plt" (literal table for ".got.plt*").  */
  s = bfd_make_section_with_flags (dynobj, ".xt.lit.plt",
				   noalloc_flags);
  if (s == NULL
      || ! bfd_set_section_alignment (dynobj, s, 2))
    return FALSE;

  return TRUE;
}


static bfd_boolean
add_extra_plt_sections (bfd *dynobj, int count)
{
  int chunk;

  /* Iterate over all chunks except 0 which uses the standard ".plt" and
     ".got.plt" sections.  */
  for (chunk = count / PLT_ENTRIES_PER_CHUNK; chunk > 0; chunk--)
    {
      char *sname;
      flagword flags;
      asection *s;

      /* Stop when we find a section has already been created.  */
      if (elf_xtensa_get_plt_section (dynobj, chunk))
	break;

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

      sname = (char *) bfd_malloc (10);
      sprintf (sname, ".plt.%u", chunk);
      s = bfd_make_section_with_flags (dynobj, sname,
				       flags | SEC_CODE);
      if (s == NULL
	  || ! bfd_set_section_alignment (dynobj, s, 2))
	return FALSE;

      sname = (char *) bfd_malloc (14);
      sprintf (sname, ".got.plt.%u", chunk);
      s = bfd_make_section_with_flags (dynobj, sname, flags);
      if (s == NULL
	  || ! bfd_set_section_alignment (dynobj, s, 2))
	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
elf_xtensa_adjust_dynamic_symbol (struct bfd_link_info *info ATTRIBUTE_UNUSED,
				  struct elf_link_hash_entry *h)
{
  /* 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->u.weakdef)
    {
      BFD_ASSERT (h->u.weakdef->root.type == bfd_link_hash_defined
		  || h->u.weakdef->root.type == bfd_link_hash_defweak);
      h->root.u.def.section = h->u.weakdef->root.u.def.section;
      h->root.u.def.value = h->u.weakdef->root.u.def.value;
      return TRUE;
    }

  /* This is a reference to a symbol defined by a dynamic object.  The
     reference must go through the GOT, so there's no need for COPY relocs,
     .dynbss, etc.  */

  return TRUE;
}


static bfd_boolean
elf_xtensa_fix_refcounts (struct elf_link_hash_entry *h, void *arg)
{
  struct bfd_link_info *info = (struct bfd_link_info *) arg;

  if (h->root.type == bfd_link_hash_warning)
    h = (struct elf_link_hash_entry *) h->root.u.i.link;

  if (! xtensa_elf_dynamic_symbol_p (h, info))
    elf_xtensa_make_sym_local (info, h);

  return TRUE;
}


static bfd_boolean
elf_xtensa_allocate_plt_size (struct elf_link_hash_entry *h, void *arg)
{
  asection *srelplt = (asection *) arg;

  if (h->root.type == bfd_link_hash_warning)
    h = (struct elf_link_hash_entry *) h->root.u.i.link;

  if (h->plt.refcount > 0)
    srelplt->size += (h->plt.refcount * sizeof (Elf32_External_Rela));

  return TRUE;
}


static bfd_boolean
elf_xtensa_allocate_got_size (struct elf_link_hash_entry *h, void *arg)
{
  asection *srelgot = (asection *) arg;

  if (h->root.type == bfd_link_hash_warning)
    h = (struct elf_link_hash_entry *) h->root.u.i.link;

  if (h->got.refcount > 0)
    srelgot->size += (h->got.refcount * sizeof (Elf32_External_Rela));

  return TRUE;
}


static void
elf_xtensa_allocate_local_got_size (struct bfd_link_info *info,
				    asection *srelgot)
{
  bfd *i;

  for (i = info->input_bfds; i; i = i->link_next)
    {
      bfd_signed_vma *local_got_refcounts;
      bfd_size_type j, cnt;
      Elf_Internal_Shdr *symtab_hdr;

      local_got_refcounts = elf_local_got_refcounts (i);
      if (!local_got_refcounts)
	continue;

      symtab_hdr = &elf_tdata (i)->symtab_hdr;
      cnt = symtab_hdr->sh_info;

      for (j = 0; j < cnt; ++j)
	{
	  if (local_got_refcounts[j] > 0)
	    srelgot->size += (local_got_refcounts[j]
			      * sizeof (Elf32_External_Rela));
	}
    }
}


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

static bfd_boolean
elf_xtensa_size_dynamic_sections (bfd *output_bfd ATTRIBUTE_UNUSED,
				  struct bfd_link_info *info)
{
  bfd *dynobj, *abfd;
  asection *s, *srelplt, *splt, *sgotplt, *srelgot, *spltlittbl, *sgotloc;
  bfd_boolean relplt, relgot;
  int plt_entries, plt_chunks, chunk;

  plt_entries = 0;
  plt_chunks = 0;
  srelgot = 0;

  dynobj = elf_hash_table (info)->dynobj;
  if (dynobj == NULL)
    abort ();

  if (elf_hash_table (info)->dynamic_sections_created)
    {
      /* Set the contents of the .interp section to the interpreter.  */
      if (info->executable)
	{
	  s = bfd_get_section_by_name (dynobj, ".interp");
	  if (s == NULL)
	    abort ();
	  s->size = sizeof ELF_DYNAMIC_INTERPRETER;
	  s->contents = (unsigned char *) ELF_DYNAMIC_INTERPRETER;
	}

      /* Allocate room for one word in ".got".  */
      s = bfd_get_section_by_name (dynobj, ".got");
      if (s == NULL)
	abort ();
      s->size = 4;

      /* Adjust refcounts for symbols that we now know are not "dynamic".  */
      elf_link_hash_traverse (elf_hash_table (info),
			      elf_xtensa_fix_refcounts,
			      (void *) info);

      /* Allocate space in ".rela.got" for literals that reference
	 global symbols.  */
      srelgot = bfd_get_section_by_name (dynobj, ".rela.got");
      if (srelgot == NULL)
	abort ();
      elf_link_hash_traverse (elf_hash_table (info),
			      elf_xtensa_allocate_got_size,
			      (void *) srelgot);

      /* If we are generating a shared object, we also need space in
	 ".rela.got" for R_XTENSA_RELATIVE relocs for literals that
	 reference local symbols.  */
      if (info->shared)
	elf_xtensa_allocate_local_got_size (info, srelgot);

      /* Allocate space in ".rela.plt" for literals that have PLT entries.  */
      srelplt = bfd_get_section_by_name (dynobj, ".rela.plt");
      if (srelplt == NULL)
	abort ();
      elf_link_hash_traverse (elf_hash_table (info),
			      elf_xtensa_allocate_plt_size,
			      (void *) srelplt);

      /* Allocate space in ".plt" to match the size of ".rela.plt".  For
	 each PLT entry, we need the PLT code plus a 4-byte literal.
	 For each chunk of ".plt", we also need two more 4-byte
	 literals, two corresponding entries in ".rela.got", and an
	 8-byte entry in ".xt.lit.plt".  */
      spltlittbl = bfd_get_section_by_name (dynobj, ".xt.lit.plt");
      if (spltlittbl == NULL)
	abort ();

      plt_entries = srelplt->size / sizeof (Elf32_External_Rela);
      plt_chunks =
	(plt_entries + PLT_ENTRIES_PER_CHUNK - 1) / PLT_ENTRIES_PER_CHUNK;

      /* Iterate over all the PLT chunks, including any extra sections
	 created earlier because the initial count of PLT relocations
	 was an overestimate.  */
      for (chunk = 0;
	   (splt = elf_xtensa_get_plt_section (dynobj, chunk)) != NULL;
	   chunk++)
	{
	  int chunk_entries;

	  sgotplt = elf_xtensa_get_gotplt_section (dynobj, chunk);
	  if (sgotplt == NULL)
	    abort ();

	  if (chunk < plt_chunks - 1)
	    chunk_entries = PLT_ENTRIES_PER_CHUNK;
	  else if (chunk == plt_chunks - 1)
	    chunk_entries = plt_entries - (chunk * PLT_ENTRIES_PER_CHUNK);
	  else
	    chunk_entries = 0;

	  if (chunk_entries != 0)
	    {
	      sgotplt->size = 4 * (chunk_entries + 2);
	      splt->size = PLT_ENTRY_SIZE * chunk_entries;
	      srelgot->size += 2 * sizeof (Elf32_External_Rela);
	      spltlittbl->size += 8;
	    }
	  else
	    {
	      sgotplt->size = 0;
	      splt->size = 0;
	    }
	}

      /* Allocate space in ".got.loc" to match the total size of all the
	 literal tables.  */
      sgotloc = bfd_get_section_by_name (dynobj, ".got.loc");
      if (sgotloc == NULL)
	abort ();
      sgotloc->size = spltlittbl->size;
      for (abfd = info->input_bfds; abfd != NULL; abfd = abfd->link_next)
	{
	  if (abfd->flags & DYNAMIC)
	    continue;
	  for (s = abfd->sections; s != NULL; s = s->next)
	    {
	      if (! elf_discarded_section (s)
		  && xtensa_is_littable_section (s)
		  && s != spltlittbl)
		sgotloc->size += s->size;
	    }
	}
    }

  /* Allocate memory for dynamic sections.  */
  relplt = FALSE;
  relgot = FALSE;
  for (s = dynobj->sections; s != NULL; s = s->next)
    {
      const char *name;
      bfd_boolean strip;

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

      /* It's OK to base decisions on the section name, because none
	 of the dynobj section names depend upon the input files.  */
      name = bfd_get_section_name (dynobj, s);

      strip = FALSE;

      if (strncmp (name, ".rela", 5) == 0)
	{
	  if (strcmp (name, ".rela.plt") == 0)
	    relplt = TRUE;
	  else if (strcmp (name, ".rela.got") == 0)
	    relgot = 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 if (strncmp (name, ".plt.", 5) == 0
	       || strncmp (name, ".got.plt.", 9) == 0)
	{
	  if (s->size == 0)
	    {
	      /* If we don't need this section, strip it from the output
		 file.  We must create the ".plt*" and ".got.plt*"
		 sections in create_dynamic_sections and/or check_relocs
		 based on a conservative estimate of the PLT relocation
		 count, because the sections must be created before the
		 linker maps input sections to output sections.  The
		 linker does that before size_dynamic_sections, where we
		 compute the exact size of the PLT, so there may be more
		 of these sections than are actually needed.  */
	      strip = TRUE;
	    }
	}
      else if (strcmp (name, ".got") != 0
	       && strcmp (name, ".plt") != 0
	       && strcmp (name, ".got.plt") != 0
	       && strcmp (name, ".xt.lit.plt") != 0
	       && strcmp (name, ".got.loc") != 0)
	{
	  /* It's not one of our sections, so don't allocate space.  */
	  continue;
	}

      if (strip)
	s->flags |= SEC_EXCLUDE;
      else
	{
	  /* Allocate memory for the section contents.  */
	  s->contents = (bfd_byte *) bfd_zalloc (dynobj, s->size);
	  if (s->contents == NULL && s->size != 0)
	    return FALSE;
	}
    }

  if (elf_hash_table (info)->dynamic_sections_created)
    {
      /* Add the special XTENSA_RTLD relocations now.  The offsets won't be
	 known until finish_dynamic_sections, but we need to get the relocs
	 in place before they are sorted.  */
      if (srelgot == NULL)
	abort ();
      for (chunk = 0; chunk < plt_chunks; chunk++)
	{
	  Elf_Internal_Rela irela;
	  bfd_byte *loc;

	  irela.r_offset = 0;
	  irela.r_info = ELF32_R_INFO (0, R_XTENSA_RTLD);
	  irela.r_addend = 0;

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

      /* Add some entries to the .dynamic section.  We fill in the
	 values later, in elf_xtensa_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 (! info->shared)
	{
	  if (!add_dynamic_entry (DT_DEBUG, 0))
	    return FALSE;
	}

      if (relplt)
	{
	  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;
	}

      if (relgot)
	{
	  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 (!add_dynamic_entry (DT_XTENSA_GOT_LOC_OFF, 0)
	  || !add_dynamic_entry (DT_XTENSA_GOT_LOC_SZ, 0))
	return FALSE;
    }
#undef add_dynamic_entry

  return TRUE;
}


/* Remove any PT_LOAD segments with no allocated sections.  Prior to
   binutils 2.13, this function used to remove the non-SEC_ALLOC
   sections from PT_LOAD segments, but that task has now been moved
   into elf.c.  We still need this function to remove any empty
   segments that result, but there's nothing Xtensa-specific about
   this and it probably ought to be moved into elf.c as well.  */

static bfd_boolean
elf_xtensa_modify_segment_map (bfd *abfd,
			       struct bfd_link_info *info ATTRIBUTE_UNUSED)
{
  struct elf_segment_map **m_p;

  m_p = &elf_tdata (abfd)->segment_map;
  while (*m_p)
    {
      if ((*m_p)->p_type == PT_LOAD && (*m_p)->count == 0)
	*m_p = (*m_p)->next;
      else
	m_p = &(*m_p)->next;
    }
  return TRUE;
}


/* Perform the specified relocation.  The instruction at (contents + address)
   is modified to set one operand to represent the value in "relocation".  The
   operand position is determined by the relocation type recorded in the
   howto.  */

#define CALL_SEGMENT_BITS (30)
#define CALL_SEGMENT_SIZE (1 << CALL_SEGMENT_BITS)

static bfd_reloc_status_type
elf_xtensa_do_reloc (reloc_howto_type *howto,
		     bfd *abfd,
		     asection *input_section,
		     bfd_vma relocation,
		     bfd_byte *contents,
		     bfd_vma address,
		     bfd_boolean is_weak_undef,
		     char **error_message)
{
  xtensa_format fmt;
  xtensa_opcode opcode;
  xtensa_isa isa = xtensa_default_isa;
  static xtensa_insnbuf ibuff = NULL;
  static xtensa_insnbuf sbuff = NULL;
  bfd_vma self_address = 0;
  bfd_size_type input_size;
  int opnd, slot;
  uint32 newval;

  if (!ibuff)
    {
      ibuff = xtensa_insnbuf_alloc (isa);
      sbuff = xtensa_insnbuf_alloc (isa);
    }

  input_size = bfd_get_section_limit (abfd, input_section);

  switch (howto->type)
    {
    case R_XTENSA_NONE:
    case R_XTENSA_DIFF8:
    case R_XTENSA_DIFF16:
    case R_XTENSA_DIFF32:
      return bfd_reloc_ok;

    case R_XTENSA_ASM_EXPAND:
      if (!is_weak_undef)
	{
	  /* Check for windowed CALL across a 1GB boundary.  */
	  xtensa_opcode opcode =
	    get_expanded_call_opcode (contents + address,
				      input_size - address, 0);
	  if (is_windowed_call_opcode (opcode))
	    {
	      self_address = (input_section->output_section->vma
			      + input_section->output_offset
			      + address);
	      if ((self_address >> CALL_SEGMENT_BITS)
		  != (relocation >> CALL_SEGMENT_BITS)) 
		{
		  *error_message = "windowed longcall crosses 1GB boundary; "
		    "return may fail";
		  return bfd_reloc_dangerous;
		}
	    }
	}
      return bfd_reloc_ok;

    case R_XTENSA_ASM_SIMPLIFY:
      {
        /* Convert the L32R/CALLX to CALL.  */
	bfd_reloc_status_type retval =
	  elf_xtensa_do_asm_simplify (contents, address, input_size,
				      error_message);
	if (retval != bfd_reloc_ok)
	  return bfd_reloc_dangerous;

	/* The CALL needs to be relocated.  Continue below for that part.  */
	address += 3;
	howto = &elf_howto_table[(unsigned) R_XTENSA_SLOT0_OP ];
      }
      break;

    case R_XTENSA_32:
    case R_XTENSA_PLT:
      {
	bfd_vma x;
	x = bfd_get_32 (abfd, contents + address);
	x = x + relocation;
	bfd_put_32 (abfd, x, contents + address);
      }
      return bfd_reloc_ok;
    }

  /* Only instruction slot-specific relocations handled below.... */
  slot = get_relocation_slot (howto->type);
  if (slot == XTENSA_UNDEFINED)
    {
      *error_message = "unexpected relocation";
      return bfd_reloc_dangerous;
    }

  /* Read the instruction into a buffer and decode the opcode.  */
  xtensa_insnbuf_from_chars (isa, ibuff, contents + address,
			     input_size - address);
  fmt = xtensa_format_decode (isa, ibuff);
  if (fmt == XTENSA_UNDEFINED)
    {
      *error_message = "cannot decode instruction format";
      return bfd_reloc_dangerous;
    }

  xtensa_format_get_slot (isa, fmt, slot, ibuff, sbuff);

  opcode = xtensa_opcode_decode (isa, fmt, slot, sbuff);
  if (opcode == XTENSA_UNDEFINED)
    {
      *error_message = "cannot decode instruction opcode";
      return bfd_reloc_dangerous;
    }

  /* Check for opcode-specific "alternate" relocations.  */
  if (is_alt_relocation (howto->type))
    {
      if (opcode == get_l32r_opcode ())
	{
	  /* Handle the special-case of non-PC-relative L32R instructions.  */
	  bfd *output_bfd = input_section->output_section->owner;
	  asection *lit4_sec = bfd_get_section_by_name (output_bfd, ".lit4");
	  if (!lit4_sec)
	    {
	      *error_message = "relocation references missing .lit4 section";
	      return bfd_reloc_dangerous;
	    }
	  self_address = ((lit4_sec->vma & ~0xfff)
			  + 0x40000 - 3); /* -3 to compensate for do_reloc */
	  newval = relocation;
	  opnd = 1;
	}
      else if (opcode == get_const16_opcode ())
	{
	  /* ALT used for high 16 bits.  */
	  newval = relocation >> 16;
	  opnd = 1;
	}
      else
	{
	  /* No other "alternate" relocations currently defined.  */
	  *error_message = "unexpected relocation";
	  return bfd_reloc_dangerous;
	}
    }
  else /* Not an "alternate" relocation.... */
    {
      if (opcode == get_const16_opcode ())
	{
	  newval = relocation & 0xffff;
	  opnd = 1;
	}
      else
	{
	  /* ...normal PC-relative relocation.... */

	  /* Determine which operand is being relocated.  */
	  opnd = get_relocation_opnd (opcode, howto->type);
	  if (opnd == XTENSA_UNDEFINED)
	    {
	      *error_message = "unexpected relocation";
	      return bfd_reloc_dangerous;
	    }

	  if (!howto->pc_relative)
	    {
	      *error_message = "expected PC-relative relocation";
	      return bfd_reloc_dangerous;
	    }

	  /* Calculate the PC address for this instruction.  */
	  self_address = (input_section->output_section->vma
			  + input_section->output_offset
			  + address);

	  newval = relocation;
	}
    }

  /* Apply the relocation.  */
  if (xtensa_operand_do_reloc (isa, opcode, opnd, &newval, self_address)
      || xtensa_operand_encode (isa, opcode, opnd, &newval)
      || xtensa_operand_set_field (isa, opcode, opnd, fmt, slot,
				   sbuff, newval))
    {
      *error_message = build_encoding_error_message (opcode, relocation);
      return bfd_reloc_dangerous;
    }

  /* Check for calls across 1GB boundaries.  */
  if (is_direct_call_opcode (opcode)
      && is_windowed_call_opcode (opcode))
    {
      if ((self_address >> CALL_SEGMENT_BITS)
	  != (relocation >> CALL_SEGMENT_BITS)) 
	{
	  *error_message =
	    "windowed call crosses 1GB boundary; return may fail";
	  return bfd_reloc_dangerous;
	}
    }

  /* Write the modified instruction back out of the buffer.  */
  xtensa_format_set_slot (isa, fmt, slot, ibuff, sbuff);
  xtensa_insnbuf_to_chars (isa, ibuff, contents + address,
			   input_size - address);
  return bfd_reloc_ok;
}


static char *
vsprint_msg (const char *origmsg, const char *fmt, int arglen, ...)
{
  /* To reduce the size of the memory leak,
     we only use a single message buffer.  */
  static bfd_size_type alloc_size = 0;
  static char *message = NULL;
  bfd_size_type orig_len, len = 0;
  bfd_boolean is_append;

  VA_OPEN (ap, arglen);
  VA_FIXEDARG (ap, const char *, origmsg);
  
  is_append = (origmsg == message);  

  orig_len = strlen (origmsg);
  len = orig_len + strlen (fmt) + arglen + 20;
  if (len > alloc_size)
    {
      message = (char *) bfd_realloc (message, len);
      alloc_size = len;
    }
  if (!is_append)
    memcpy (message, origmsg, orig_len);
  vsprintf (message + orig_len, fmt, ap);
  VA_CLOSE (ap);
  return message;
}


static char *
build_encoding_error_message (xtensa_opcode opcode, bfd_vma target_address)
{
  const char *opname = xtensa_opcode_name (xtensa_default_isa, opcode);
  const char *msg;

  msg = "cannot encode";
  if (is_direct_call_opcode (opcode))
    {
      if ((target_address & 0x3) != 0)
	msg = "misaligned call target";
      else
	msg = "call target out of range";
    }
  else if (opcode == get_l32r_opcode ())
    {
      if ((target_address & 0x3) != 0)
	msg = "misaligned literal target";
      else
	msg = "literal target out of range";
    }

  return vsprint_msg (opname, ": %s", strlen (msg) + 2, msg);
}


/* This function is registered as the "special_function" in the
   Xtensa howto for handling simplify operations.
   bfd_perform_relocation / bfd_install_relocation use it to
   perform (install) the specified relocation.  Since this replaces the code
   in bfd_perform_relocation, it is basically an Xtensa-specific,
   stripped-down version of bfd_perform_relocation.  */

static bfd_reloc_status_type
bfd_elf_xtensa_reloc (bfd *abfd,
		      arelent *reloc_entry,
		      asymbol *symbol,
		      void *data,
		      asection *input_section,
		      bfd *output_bfd,
		      char **error_message)
{
  bfd_vma relocation;
  bfd_reloc_status_type flag;
  bfd_size_type octets = reloc_entry->address * bfd_octets_per_byte (abfd);
  bfd_vma output_base = 0;
  reloc_howto_type *howto = reloc_entry->howto;
  asection *reloc_target_output_section;
  bfd_boolean is_weak_undef;

  if (!xtensa_default_isa)
    xtensa_default_isa = xtensa_isa_init (0, 0);

  /* ELF relocs are against symbols.  If we are producing relocatable
     output, and the reloc is against an external symbol, the resulting
     reloc will also be against the same symbol.  In such a case, we
     don't want to change anything about the way the reloc is handled,
     since it will all be done at final link time.  This test is similar
     to what bfd_elf_generic_reloc does except that it lets relocs with
     howto->partial_inplace go through even if the addend is non-zero.
     (The real problem is that partial_inplace is set for XTENSA_32
     relocs to begin with, but that's a long story and there's little we
     can do about it now....)  */

  if (output_bfd && (symbol->flags & BSF_SECTION_SYM) == 0)
    {
      reloc_entry->address += input_section->output_offset;
      return bfd_reloc_ok;
    }

  /* Is the address of the relocation really within the section?  */
  if (reloc_entry->address > bfd_get_section_limit (abfd, input_section))
    return bfd_reloc_outofrange;

  /* Work out which section the relocation is targeted at and the
     initial relocation command value.  */

  /* Get symbol value.  (Common symbols are special.)  */
  if (bfd_is_com_section (symbol->section))
    relocation = 0;
  else
    relocation = symbol->value;

  reloc_target_output_section = symbol->section->output_section;

  /* Convert input-section-relative symbol value to absolute.  */
  if ((output_bfd && !howto->partial_inplace)
      || reloc_target_output_section == NULL)
    output_base = 0;
  else
    output_base = reloc_target_output_section->vma;

  relocation += output_base + symbol->section->output_offset;

  /* Add in supplied addend.  */
  relocation += reloc_entry->addend;

  /* Here the variable relocation holds the final address of the
     symbol we are relocating against, plus any addend.  */
  if (output_bfd)
    {
      if (!howto->partial_inplace)
	{
	  /* This is a partial relocation, and we want to apply the relocation
	     to the reloc entry rather than the raw data.  Everything except
	     relocations against section symbols has already been handled
	     above.  */

	  BFD_ASSERT (symbol->flags & BSF_SECTION_SYM);
	  reloc_entry->addend = relocation;
	  reloc_entry->address += input_section->output_offset;
	  return bfd_reloc_ok;
	}
      else
	{
	  reloc_entry->address += input_section->output_offset;
	  reloc_entry->addend = 0;
	}
    }

  is_weak_undef = (bfd_is_und_section (symbol->section)
		   && (symbol->flags & BSF_WEAK) != 0);
  flag = elf_xtensa_do_reloc (howto, abfd, input_section, relocation,
			      (bfd_byte *) data, (bfd_vma) octets,
			      is_weak_undef, error_message);

  if (flag == bfd_reloc_dangerous)
    {
      /* Add the symbol name to the error message.  */
      if (! *error_message)
	*error_message = "";
      *error_message = vsprint_msg (*error_message, ": (%s + 0x%lx)",
				    strlen (symbol->name) + 17,
				    symbol->name, reloc_entry->addend);
    }

  return flag;
}


/* Set up an entry in the procedure linkage table.  */

static bfd_vma
elf_xtensa_create_plt_entry (bfd *dynobj,
			     bfd *output_bfd,
			     unsigned reloc_index)
{
  asection *splt, *sgotplt;
  bfd_vma plt_base, got_base;
  bfd_vma code_offset, lit_offset;
  int chunk;

  chunk = reloc_index / PLT_ENTRIES_PER_CHUNK;
  splt = elf_xtensa_get_plt_section (dynobj, chunk);
  sgotplt = elf_xtensa_get_gotplt_section (dynobj, chunk);
  BFD_ASSERT (splt != NULL && sgotplt != NULL);

  plt_base = splt->output_section->vma + splt->output_offset;
  got_base = sgotplt->output_section->vma + sgotplt->output_offset;

  lit_offset = 8 + (reloc_index % PLT_ENTRIES_PER_CHUNK) * 4;
  code_offset = (reloc_index % PLT_ENTRIES_PER_CHUNK) * PLT_ENTRY_SIZE;

  /* Fill in the literal entry.  This is the offset of the dynamic
     relocation entry.  */
  bfd_put_32 (output_bfd, reloc_index * sizeof (Elf32_External_Rela),
	      sgotplt->contents + lit_offset);

  /* Fill in the entry in the procedure linkage table.  */
  memcpy (splt->contents + code_offset,
	  (bfd_big_endian (output_bfd)
	   ? elf_xtensa_be_plt_entry
	   : elf_xtensa_le_plt_entry),
	  PLT_ENTRY_SIZE);
  bfd_put_16 (output_bfd, l32r_offset (got_base + 0,
				       plt_base + code_offset + 3),
	      splt->contents + code_offset + 4);
  bfd_put_16 (output_bfd, l32r_offset (got_base + 4,
				       plt_base + code_offset + 6),
	      splt->contents + code_offset + 7);
  bfd_put_16 (output_bfd, l32r_offset (got_base + lit_offset,
				       plt_base + code_offset + 9),
	      splt->contents + code_offset + 10);

  return plt_base + code_offset;
}


/* Relocate an Xtensa ELF section.  This is invoked by the linker for
   both relocatable and final links.  */

static bfd_boolean
elf_xtensa_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)
{
  Elf_Internal_Shdr *symtab_hdr;
  Elf_Internal_Rela *rel;
  Elf_Internal_Rela *relend;
  struct elf_link_hash_entry **sym_hashes;
  asection *srelgot, *srelplt;
  bfd *dynobj;
  property_table_entry *lit_table = 0;
  int ltblsize = 0;
  char *error_message = NULL;
  bfd_size_type input_size;

  if (!xtensa_default_isa)
    xtensa_default_isa = xtensa_isa_init (0, 0);

  dynobj = elf_hash_table (info)->dynobj;
  symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;
  sym_hashes = elf_sym_hashes (input_bfd);

  srelgot = NULL;
  srelplt = NULL;
  if (dynobj)
    {
      srelgot = bfd_get_section_by_name (dynobj, ".rela.got");;
      srelplt = bfd_get_section_by_name (dynobj, ".rela.plt");
    }

  if (elf_hash_table (info)->dynamic_sections_created)
    {
      ltblsize = xtensa_read_table_entries (input_bfd, input_section,
					    &lit_table, XTENSA_LIT_SEC_NAME,
					    TRUE);
      if (ltblsize < 0)
	return FALSE;
    }

  input_size = bfd_get_section_limit (input_bfd, input_section);

  rel = relocs;
  relend = relocs + input_section->reloc_count;
  for (; rel < relend; rel++)
    {
      int r_type;
      reloc_howto_type *howto;
      unsigned long r_symndx;
      struct elf_link_hash_entry *h;
      Elf_Internal_Sym *sym;
      asection *sec;
      bfd_vma relocation;
      bfd_reloc_status_type r;
      bfd_boolean is_weak_undef;
      bfd_boolean unresolved_reloc;
      bfd_boolean warned;

      r_type = ELF32_R_TYPE (rel->r_info);
      if (r_type == (int) R_XTENSA_GNU_VTINHERIT
	  || r_type == (int) R_XTENSA_GNU_VTENTRY)
	continue;

      if (r_type < 0 || r_type >= (int) R_XTENSA_max)
	{
	  bfd_set_error (bfd_error_bad_value);
	  return FALSE;
	}
      howto = &elf_howto_table[r_type];

      r_symndx = ELF32_R_SYM (rel->r_info);

      if (info->relocatable)
	{
	  /* This is a relocatable link.
	     1) If the reloc is against a section symbol, adjust
	     according to the output section.
	     2) If there is a new target for this relocation,
	     the new target will be in the same output section.
	     We adjust the relocation by the output section
	     difference.  */

	  if (relaxing_section)
	    {
	      /* Check if this references a section in another input file.  */
	      if (!do_fix_for_relocatable_link (rel, input_bfd, input_section,
						contents))
		return FALSE;
	      r_type = ELF32_R_TYPE (rel->r_info);
	    }

	  if (r_type == R_XTENSA_ASM_SIMPLIFY)
	    {
	      char *error_message = NULL;
	      /* Convert ASM_SIMPLIFY into the simpler relocation
		 so that they never escape a relaxing link.  */
	      r = contract_asm_expansion (contents, input_size, rel,
					  &error_message);
	      if (r != bfd_reloc_ok)
		{
		  if (!((*info->callbacks->reloc_dangerous)
			(info, error_message, input_bfd, input_section,
			 rel->r_offset)))
		    return FALSE;
		}
	      r_type = ELF32_R_TYPE (rel->r_info);
	    }

	  /* This is a relocatable link, so 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 (r_symndx < symtab_hdr->sh_info)
	    {
	      sym = local_syms + r_symndx;
	      if (ELF_ST_TYPE (sym->st_info) == STT_SECTION)
		{
		  sec = local_sections[r_symndx];
		  rel->r_addend += sec->output_offset + sym->st_value;
		}
	    }

	  /* If there is an addend with a partial_inplace howto,
	     then move the addend to the contents.  This is a hack
	     to work around problems with DWARF in relocatable links
	     with some previous version of BFD.  Now we can't easily get
	     rid of the hack without breaking backward compatibility.... */
	  if (rel->r_addend)
	    {
	      howto = &elf_howto_table[r_type];
	      if (howto->partial_inplace)
		{
		  r = elf_xtensa_do_reloc (howto, input_bfd, input_section,
					   rel->r_addend, contents,
					   rel->r_offset, FALSE,
					   &error_message);
		  if (r != bfd_reloc_ok)
		    {
		      if (!((*info->callbacks->reloc_dangerous)
			    (info, error_message, input_bfd, input_section,
			     rel->r_offset)))
			return FALSE;
		    }
		  rel->r_addend = 0;
		}
	    }

	  /* Done with work for relocatable link; continue with next reloc.  */
	  continue;
	}

      /* This is a final link.  */

      h = NULL;
      sym = NULL;
      sec = NULL;
      is_weak_undef = FALSE;
      unresolved_reloc = FALSE;
      warned = FALSE;

      if (howto->partial_inplace)
	{
	  /* Because R_XTENSA_32 was made partial_inplace to fix some
	     problems with DWARF info in partial links, there may be
	     an addend stored in the contents.  Take it out of there
	     and move it back into the addend field of the reloc.  */
	  rel->r_addend += bfd_get_32 (input_bfd, contents + rel->r_offset);
	  bfd_put_32 (input_bfd, 0, contents + rel->r_offset);
	}

      if (r_symndx < symtab_hdr->sh_info)
	{
	  sym = local_syms + r_symndx;
	  sec = local_sections[r_symndx];
	  relocation = _bfd_elf_rela_local_sym (output_bfd, sym, &sec, rel);
	}
      else
	{
	  RELOC_FOR_GLOBAL_SYMBOL (info, input_bfd, input_section, rel,
				   r_symndx, symtab_hdr, sym_hashes,
				   h, sec, relocation,
				   unresolved_reloc, warned);

	  if (relocation == 0
	      && !unresolved_reloc
	      && h->root.type == bfd_link_hash_undefweak)
	    is_weak_undef = TRUE;
	}

      if (relaxing_section)
	{
	  /* Check if this references a section in another input file.  */
	  do_fix_for_final_link (rel, input_bfd, input_section, contents,
				 &relocation);

	  /* Update some already cached values.  */
	  r_type = ELF32_R_TYPE (rel->r_info);
	  howto = &elf_howto_table[r_type];
	}

      /* Sanity check the address.  */
      if (rel->r_offset >= input_size
	  && ELF32_R_TYPE (rel->r_info) != R_XTENSA_NONE)
	{
	  (*_bfd_error_handler)
	    (_("%B(%A+0x%lx): relocation offset out of range (size=0x%x)"),
	     input_bfd, input_section, rel->r_offset, input_size);
	  bfd_set_error (bfd_error_bad_value);
	  return FALSE;
	}

      /* Generate dynamic relocations.  */
      if (elf_hash_table (info)->dynamic_sections_created)
	{
	  bfd_boolean dynamic_symbol = xtensa_elf_dynamic_symbol_p (h, info);

	  if (dynamic_symbol && is_operand_relocation (r_type))
	    {
	      /* This is an error.  The symbol's real value won't be known
		 until runtime and it's likely to be out of range anyway.  */
	      const char *name = h->root.root.string;
	      error_message = vsprint_msg ("invalid relocation for dynamic "
					   "symbol", ": %s",
					   strlen (name) + 2, name);
	      if (!((*info->callbacks->reloc_dangerous)
		    (info, error_message, input_bfd, input_section,
		     rel->r_offset)))
		return FALSE;
	    }
	  else if ((r_type == R_XTENSA_32 || r_type == R_XTENSA_PLT)
		   && (input_section->flags & SEC_ALLOC) != 0
		   && (dynamic_symbol || info->shared))
	    {
	      Elf_Internal_Rela outrel;
	      bfd_byte *loc;
	      asection *srel;

	      if (dynamic_symbol && r_type == R_XTENSA_PLT)
		srel = srelplt;
	      else
		srel = srelgot;

	      BFD_ASSERT (srel != NULL);

	      outrel.r_offset =
		_bfd_elf_section_offset (output_bfd, info,
					 input_section, rel->r_offset);

	      if ((outrel.r_offset | 1) == (bfd_vma) -1)
		memset (&outrel, 0, sizeof outrel);
	      else
		{
		  outrel.r_offset += (input_section->output_section->vma
				      + input_section->output_offset);

		  /* Complain if the relocation is in a read-only section
		     and not in a literal pool.  */
		  if ((input_section->flags & SEC_READONLY) != 0
		      && !elf_xtensa_in_literal_pool (lit_table, ltblsize,
						      outrel.r_offset))
		    {
		      error_message =
			_("dynamic relocation in read-only section");
		      if (!((*info->callbacks->reloc_dangerous)
			    (info, error_message, input_bfd, input_section,
			     rel->r_offset)))
			return FALSE;
		    }

		  if (dynamic_symbol)
		    {
		      outrel.r_addend = rel->r_addend;
		      rel->r_addend = 0;

		      if (r_type == R_XTENSA_32)
			{
			  outrel.r_info =
			    ELF32_R_INFO (h->dynindx, R_XTENSA_GLOB_DAT);
			  relocation = 0;
			}
		      else /* r_type == R_XTENSA_PLT */
			{
			  outrel.r_info =
			    ELF32_R_INFO (h->dynindx, R_XTENSA_JMP_SLOT);

			  /* Create the PLT entry and set the initial
			     contents of the literal entry to the address of
			     the PLT entry.  */
			  relocation =
			    elf_xtensa_create_plt_entry (dynobj, output_bfd,
							 srel->reloc_count);
			}
		      unresolved_reloc = FALSE;
		    }
		  else
		    {
		      /* Generate a RELATIVE relocation.  */
		      outrel.r_info = ELF32_R_INFO (0, R_XTENSA_RELATIVE);
		      outrel.r_addend = 0;
		    }
		}

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

      /* Dynamic relocs are not propagated for SEC_DEBUGGING sections
	 because such sections are not SEC_ALLOC and thus ld.so will
	 not process them.  */
      if (unresolved_reloc
	  && !((input_section->flags & SEC_DEBUGGING) != 0
	       && h->def_dynamic))
	(*_bfd_error_handler)
	  (_("%B(%A+0x%lx): unresolvable relocation against symbol `%s'"),
	   input_bfd,
	   input_section,
	   (long) rel->r_offset,
	   h->root.root.string);

      /* There's no point in calling bfd_perform_relocation here.
	 Just go directly to our "special function".  */
      r = elf_xtensa_do_reloc (howto, input_bfd, input_section,
			       relocation + rel->r_addend,
			       contents, rel->r_offset, is_weak_undef,
			       &error_message);

      if (r != bfd_reloc_ok && !warned)
	{
	  const char *name;

	  BFD_ASSERT (r == bfd_reloc_dangerous || r == bfd_reloc_other);
	  BFD_ASSERT (error_message != NULL);

	  if (h)
	    name = h->root.root.string;
	  else
	    {
	      name = bfd_elf_string_from_elf_section
		(input_bfd, symtab_hdr->sh_link, sym->st_name);
	      if (name && *name == '\0')
		name = bfd_section_name (input_bfd, sec);
	    }
	  if (name)
	    {
	      if (rel->r_addend == 0)
		error_message = vsprint_msg (error_message, ": %s",
					     strlen (name) + 2, name);
	      else
		error_message = vsprint_msg (error_message, ": (%s+0x%x)",
					     strlen (name) + 22,
					     name, rel->r_addend);
	    }

	  if (!((*info->callbacks->reloc_dangerous)
		(info, error_message, input_bfd, input_section,
		 rel->r_offset)))
	    return FALSE;
	}
    }

  if (lit_table)
    free (lit_table);

  input_section->reloc_done = TRUE;

  return TRUE;
}


/* Finish up dynamic symbol handling.  There's not much to do here since
   the PLT and GOT entries are all set up by relocate_section.  */

static bfd_boolean
elf_xtensa_finish_dynamic_symbol (bfd *output_bfd ATTRIBUTE_UNUSED,
				  struct bfd_link_info *info ATTRIBUTE_UNUSED,
				  struct elf_link_hash_entry *h,
				  Elf_Internal_Sym *sym)
{
  if (h->needs_plt
      && !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;
    }

  /* Mark _DYNAMIC and _GLOBAL_OFFSET_TABLE_ as absolute.  */
  if (strcmp (h->root.root.string, "_DYNAMIC") == 0
      || strcmp (h->root.root.string, "_GLOBAL_OFFSET_TABLE_") == 0)
    sym->st_shndx = SHN_ABS;

  return TRUE;
}


/* Combine adjacent literal table entries in the output.  Adjacent
   entries within each input section may have been removed during
   relaxation, but we repeat the process here, even though it's too late
   to shrink the output section, because it's important to minimize the
   number of literal table entries to reduce the start-up work for the
   runtime linker.  Returns the number of remaining table entries or -1
   on error.  */

static int
elf_xtensa_combine_prop_entries (bfd *output_bfd,
				 asection *sxtlit,
				 asection *sgotloc)
{
  bfd_byte *contents;
  property_table_entry *table;
  bfd_size_type section_size, sgotloc_size;
  bfd_vma offset;
  int n, m, num;

  section_size = sxtlit->size;
  BFD_ASSERT (section_size % 8 == 0);
  num = section_size / 8;

  sgotloc_size = sgotloc->size;
  if (sgotloc_size != section_size)
    {
      (*_bfd_error_handler)
	(_("internal inconsistency in size of .got.loc section"));
      return -1;
    }

  table = bfd_malloc (num * sizeof (property_table_entry));
  if (table == 0)
    return -1;

  /* The ".xt.lit.plt" section has the SEC_IN_MEMORY flag set and this
     propagates to the output section, where it doesn't really apply and
     where it breaks the following call to bfd_malloc_and_get_section.  */
  sxtlit->flags &= ~SEC_IN_MEMORY;

  if (!bfd_malloc_and_get_section (output_bfd, sxtlit, &contents))
    {
      if (contents != 0)
	free (contents);
      free (table);
      return -1;
    }

  /* There should never be any relocations left at this point, so this
     is quite a bit easier than what is done during relaxation.  */

  /* Copy the raw contents into a property table array and sort it.  */
  offset = 0;
  for (n = 0; n < num; n++)
    {
      table[n].address = bfd_get_32 (output_bfd, &contents[offset]);
      table[n].size = bfd_get_32 (output_bfd, &contents[offset + 4]);
      offset += 8;
    }
  qsort (table, num, sizeof (property_table_entry), property_table_compare);

  for (n = 0; n < num; n++)
    {
      bfd_boolean remove = FALSE;

      if (table[n].size == 0)
	remove = TRUE;
      else if (n > 0 &&
	       (table[n-1].address + table[n-1].size == table[n].address))
	{
	  table[n-1].size += table[n].size;
	  remove = TRUE;
	}

      if (remove)
	{
	  for (m = n; m < num - 1; m++)
	    {
	      table[m].address = table[m+1].address;
	      table[m].size = table[m+1].size;
	    }

	  n--;
	  num--;
	}
    }

  /* Copy the data back to the raw contents.  */
  offset = 0;
  for (n = 0; n < num; n++)
    {
      bfd_put_32 (output_bfd, table[n].address, &contents[offset]);
      bfd_put_32 (output_bfd, table[n].size, &contents[offset + 4]);
      offset += 8;
    }

  /* Clear the removed bytes.  */
  if ((bfd_size_type) (num * 8) < section_size)
    memset (&contents[num * 8], 0, section_size - num * 8);

  if (! bfd_set_section_contents (output_bfd, sxtlit, contents, 0,
				  section_size))
    return -1;

  /* Copy the contents to ".got.loc".  */
  memcpy (sgotloc->contents, contents, section_size);

  free (contents);
  free (table);
  return num;
}


/* Finish up the dynamic sections.  */

static bfd_boolean
elf_xtensa_finish_dynamic_sections (bfd *output_bfd,
				    struct bfd_link_info *info)
{
  bfd *dynobj;
  asection *sdyn, *srelplt, *sgot, *sxtlit, *sgotloc;
  Elf32_External_Dyn *dyncon, *dynconend;
  int num_xtlit_entries;

  if (! elf_hash_table (info)->dynamic_sections_created)
    return TRUE;

  dynobj = elf_hash_table (info)->dynobj;
  sdyn = bfd_get_section_by_name (dynobj, ".dynamic");
  BFD_ASSERT (sdyn != NULL);

  /* Set the first entry in the global offset table to the address of
     the dynamic section.  */
  sgot = bfd_get_section_by_name (dynobj, ".got");
  if (sgot)
    {
      BFD_ASSERT (sgot->size == 4);
      if (sdyn == NULL)
	bfd_put_32 (output_bfd, 0, sgot->contents);
      else
	bfd_put_32 (output_bfd,
		    sdyn->output_section->vma + sdyn->output_offset,
		    sgot->contents);
    }

  srelplt = bfd_get_section_by_name (dynobj, ".rela.plt");
  if (srelplt && srelplt->size != 0)
    {
      asection *sgotplt, *srelgot, *spltlittbl;
      int chunk, plt_chunks, plt_entries;
      Elf_Internal_Rela irela;
      bfd_byte *loc;
      unsigned rtld_reloc;

      srelgot = bfd_get_section_by_name (dynobj, ".rela.got");;
      BFD_ASSERT (srelgot != NULL);

      spltlittbl = bfd_get_section_by_name (dynobj, ".xt.lit.plt");
      BFD_ASSERT (spltlittbl != NULL);

      /* Find the first XTENSA_RTLD relocation.  Presumably the rest
	 of them follow immediately after....  */
      for (rtld_reloc = 0; rtld_reloc < srelgot->reloc_count; rtld_reloc++)
	{
	  loc = srelgot->contents + rtld_reloc * sizeof (Elf32_External_Rela);
	  bfd_elf32_swap_reloca_in (output_bfd, loc, &irela);
	  if (ELF32_R_TYPE (irela.r_info) == R_XTENSA_RTLD)
	    break;
	}
      BFD_ASSERT (rtld_reloc < srelgot->reloc_count);

      plt_entries = srelplt->size / sizeof (Elf32_External_Rela);
      plt_chunks =
	(plt_entries + PLT_ENTRIES_PER_CHUNK - 1) / PLT_ENTRIES_PER_CHUNK;

      for (chunk = 0; chunk < plt_chunks; chunk++)
	{
	  int chunk_entries = 0;

	  sgotplt = elf_xtensa_get_gotplt_section (dynobj, chunk);
	  BFD_ASSERT (sgotplt != NULL);

	  /* Emit special RTLD relocations for the first two entries in
	     each chunk of the .got.plt section.  */

	  loc = srelgot->contents + rtld_reloc * sizeof (Elf32_External_Rela);
	  bfd_elf32_swap_reloca_in (output_bfd, loc, &irela);
	  BFD_ASSERT (ELF32_R_TYPE (irela.r_info) == R_XTENSA_RTLD);
	  irela.r_offset = (sgotplt->output_section->vma
			    + sgotplt->output_offset);
	  irela.r_addend = 1; /* tell rtld to set value to resolver function */
	  bfd_elf32_swap_reloca_out (output_bfd, &irela, loc);
	  rtld_reloc += 1;
	  BFD_ASSERT (rtld_reloc <= srelgot->reloc_count);

	  /* Next literal immediately follows the first.  */
	  loc += sizeof (Elf32_External_Rela);
	  bfd_elf32_swap_reloca_in (output_bfd, loc, &irela);
	  BFD_ASSERT (ELF32_R_TYPE (irela.r_info) == R_XTENSA_RTLD);
	  irela.r_offset = (sgotplt->output_section->vma
			    + sgotplt->output_offset + 4);
	  /* Tell rtld to set value to object's link map.  */
	  irela.r_addend = 2;
	  bfd_elf32_swap_reloca_out (output_bfd, &irela, loc);
	  rtld_reloc += 1;
	  BFD_ASSERT (rtld_reloc <= srelgot->reloc_count);

	  /* Fill in the literal table.  */
	  if (chunk < plt_chunks - 1)
	    chunk_entries = PLT_ENTRIES_PER_CHUNK;
	  else
	    chunk_entries = plt_entries - (chunk * PLT_ENTRIES_PER_CHUNK);

	  BFD_ASSERT ((unsigned) (chunk + 1) * 8 <= spltlittbl->size);
	  bfd_put_32 (output_bfd,
		      sgotplt->output_section->vma + sgotplt->output_offset,
		      spltlittbl->contents + (chunk * 8) + 0);
	  bfd_put_32 (output_bfd,
		      8 + (chunk_entries * 4),
		      spltlittbl->contents + (chunk * 8) + 4);
	}

      /* All the dynamic relocations have been emitted at this point.
	 Make sure the relocation sections are the correct size.  */
      if (srelgot->size != (sizeof (Elf32_External_Rela)
			    * srelgot->reloc_count)
	  || srelplt->size != (sizeof (Elf32_External_Rela)
			       * srelplt->reloc_count))
	abort ();

     /* The .xt.lit.plt section has just been modified.  This must
	happen before the code below which combines adjacent literal
	table entries, and the .xt.lit.plt contents have to be forced to
	the output here.  */
      if (! bfd_set_section_contents (output_bfd,
				      spltlittbl->output_section,
				      spltlittbl->contents,
				      spltlittbl->output_offset,
				      spltlittbl->size))
	return FALSE;
      /* Clear SEC_HAS_CONTENTS so the contents won't be output again.  */
      spltlittbl->flags &= ~SEC_HAS_CONTENTS;
    }

  /* Combine adjacent literal table entries.  */
  BFD_ASSERT (! info->relocatable);
  sxtlit = bfd_get_section_by_name (output_bfd, ".xt.lit");
  sgotloc = bfd_get_section_by_name (dynobj, ".got.loc");
  BFD_ASSERT (sxtlit && sgotloc);
  num_xtlit_entries =
    elf_xtensa_combine_prop_entries (output_bfd, sxtlit, sgotloc);
  if (num_xtlit_entries < 0)
    return FALSE;

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

      bfd_elf32_swap_dyn_in (dynobj, dyncon, &dyn);

      switch (dyn.d_tag)
	{
	default:
	  break;

	case DT_XTENSA_GOT_LOC_SZ:
	  dyn.d_un.d_val = num_xtlit_entries;
	  break;

	case DT_XTENSA_GOT_LOC_OFF:
	  name = ".got.loc";
	  goto get_vma;
	case DT_PLTGOT:
	  name = ".got";
	  goto get_vma;
	case DT_JMPREL:
	  name = ".rela.plt";
	get_vma:
	  s = bfd_get_section_by_name (output_bfd, name);
	  BFD_ASSERT (s);
	  dyn.d_un.d_ptr = s->vma;
	  break;

	case DT_PLTRELSZ:
	  s = bfd_get_section_by_name (output_bfd, ".rela.plt");
	  BFD_ASSERT (s);
	  dyn.d_un.d_val = s->size;
	  break;

	case DT_RELASZ:
	  /* Adjust RELASZ to not include JMPREL.  This matches what
	     glibc expects and what is done for several other ELF
	     targets (e.g., i386, alpha), but the "correct" behavior
	     seems to be unresolved.  Since the linker script arranges
	     for .rela.plt to follow all other relocation sections, we
	     don't have to worry about changing the DT_RELA entry.  */
	  s = bfd_get_section_by_name (output_bfd, ".rela.plt");
	  if (s)
	    dyn.d_un.d_val -= s->size;
	  break;
	}

      bfd_elf32_swap_dyn_out (output_bfd, &dyn, dyncon);
    }

  return TRUE;
}


/* Functions for dealing with the e_flags field.  */

/* Merge backend specific data from an object file to the output
   object file when linking.  */

static bfd_boolean
elf_xtensa_merge_private_bfd_data (bfd *ibfd, bfd *obfd)
{
  unsigned out_mach, in_mach;
  flagword out_flag, in_flag;

  /* Check if we have the same endianess.  */
  if (!_bfd_generic_verify_endian_match (ibfd, obfd))
    return FALSE;

  /* Don't even pretend to support mixed-format linking.  */
  if (bfd_get_flavour (ibfd) != bfd_target_elf_flavour
      || bfd_get_flavour (obfd) != bfd_target_elf_flavour)
    return FALSE;

  out_flag = elf_elfheader (obfd)->e_flags;
  in_flag = elf_elfheader (ibfd)->e_flags;

  out_mach = out_flag & EF_XTENSA_MACH;
  in_mach = in_flag & EF_XTENSA_MACH;
  if (out_mach != in_mach)
    {
      (*_bfd_error_handler)
	(_("%B: incompatible machine type. Output is 0x%x. Input is 0x%x"),
	 ibfd, out_mach, in_mach);
      bfd_set_error (bfd_error_wrong_format);
      return FALSE;
    }

  if (! elf_flags_init (obfd))
    {
      elf_flags_init (obfd) = TRUE;
      elf_elfheader (obfd)->e_flags = in_flag;

      if (bfd_get_arch (obfd) == bfd_get_arch (ibfd)
	  && bfd_get_arch_info (obfd)->the_default)
	return bfd_set_arch_mach (obfd, bfd_get_arch (ibfd),
				  bfd_get_mach (ibfd));

      return TRUE;
    }

  if ((out_flag & EF_XTENSA_XT_INSN) != (in_flag & EF_XTENSA_XT_INSN)) 
    elf_elfheader (obfd)->e_flags &= (~ EF_XTENSA_XT_INSN);

  if ((out_flag & EF_XTENSA_XT_LIT) != (in_flag & EF_XTENSA_XT_LIT)) 
    elf_elfheader (obfd)->e_flags &= (~ EF_XTENSA_XT_LIT);

  return TRUE;
}


static bfd_boolean
elf_xtensa_set_private_flags (bfd *abfd, flagword flags)
{
  BFD_ASSERT (!elf_flags_init (abfd)
	      || elf_elfheader (abfd)->e_flags == flags);

  elf_elfheader (abfd)->e_flags |= flags;
  elf_flags_init (abfd) = TRUE;

  return TRUE;
}


static bfd_boolean
elf_xtensa_print_private_bfd_data (bfd *abfd, void *farg)
{
  FILE *f = (FILE *) farg;
  flagword e_flags = elf_elfheader (abfd)->e_flags;

  fprintf (f, "\nXtensa header:\n");
  if ((e_flags & EF_XTENSA_MACH) == E_XTENSA_MACH)
    fprintf (f, "\nMachine     = Base\n");
  else
    fprintf (f, "\nMachine Id  = 0x%x\n", e_flags & EF_XTENSA_MACH);

  fprintf (f, "Insn tables = %s\n",
	   (e_flags & EF_XTENSA_XT_INSN) ? "true" : "false");

  fprintf (f, "Literal tables = %s\n",
	   (e_flags & EF_XTENSA_XT_LIT) ? "true" : "false");

  return _bfd_elf_print_private_bfd_data (abfd, farg);
}


/* Set the right machine number for an Xtensa ELF file.  */

static bfd_boolean
elf_xtensa_object_p (bfd *abfd)
{
  int mach;
  unsigned long arch = elf_elfheader (abfd)->e_flags & EF_XTENSA_MACH;

  switch (arch)
    {
    case E_XTENSA_MACH:
      mach = bfd_mach_xtensa;
      break;
    default:
      return FALSE;
    }

  (void) bfd_default_set_arch_mach (abfd, bfd_arch_xtensa, mach);
  return TRUE;
}


/* The final processing done just before writing out an Xtensa ELF object
   file.  This gets the Xtensa architecture right based on the machine
   number.  */

static void
elf_xtensa_final_write_processing (bfd *abfd,
				   bfd_boolean linker ATTRIBUTE_UNUSED)
{
  int mach;
  unsigned long val;

  switch (mach = bfd_get_mach (abfd))
    {
    case bfd_mach_xtensa:
      val = E_XTENSA_MACH;
      break;
    default:
      return;
    }

  elf_elfheader (abfd)->e_flags &=  (~ EF_XTENSA_MACH);
  elf_elfheader (abfd)->e_flags |= val;
}


static enum elf_reloc_type_class
elf_xtensa_reloc_type_class (const Elf_Internal_Rela *rela)
{
  switch ((int) ELF32_R_TYPE (rela->r_info))
    {
    case R_XTENSA_RELATIVE:
      return reloc_class_relative;
    case R_XTENSA_JMP_SLOT:
      return reloc_class_plt;
    default:
      return reloc_class_normal;
    }
}


static bfd_boolean
elf_xtensa_discard_info_for_section (bfd *abfd,
				     struct elf_reloc_cookie *cookie,
				     struct bfd_link_info *info,
				     asection *sec)
{
  bfd_byte *contents;
  bfd_vma section_size;
  bfd_vma offset, actual_offset;
  size_t removed_bytes = 0;

  section_size = sec->size;
  if (section_size == 0 || section_size % 8 != 0)
    return FALSE;

  if (sec->output_section
      && bfd_is_abs_section (sec->output_section))
    return FALSE;

  contents = retrieve_contents (abfd, sec, info->keep_memory);
  if (!contents)
    return FALSE;

  cookie->rels = retrieve_internal_relocs (abfd, sec, info->keep_memory);
  if (!cookie->rels)
    {
      release_contents (sec, contents);
      return FALSE;
    }

  cookie->rel = cookie->rels;
  cookie->relend = cookie->rels + sec->reloc_count;

  for (offset = 0; offset < section_size; offset += 8)
    {
      actual_offset = offset - removed_bytes;

      /* The ...symbol_deleted_p function will skip over relocs but it
	 won't adjust their offsets, so do that here.  */
      while (cookie->rel < cookie->relend
	     && cookie->rel->r_offset < offset)
	{
	  cookie->rel->r_offset -= removed_bytes;
	  cookie->rel++;
	}

      while (cookie->rel < cookie->relend
	     && cookie->rel->r_offset == offset)
	{
	  if (bfd_elf_reloc_symbol_deleted_p (offset, cookie))
	    {
	      /* Remove the table entry.  (If the reloc type is NONE, then
		 the entry has already been merged with another and deleted
		 during relaxation.)  */
	      if (ELF32_R_TYPE (cookie->rel->r_info) != R_XTENSA_NONE)
		{
		  /* Shift the contents up.  */
		  if (offset + 8 < section_size)
		    memmove (&contents[actual_offset],
			     &contents[actual_offset+8],
			     section_size - offset - 8);
		  removed_bytes += 8;
		}

	      /* Remove this relocation.  */
	      cookie->rel->r_info = ELF32_R_INFO (0, R_XTENSA_NONE);
	    }

	  /* Adjust the relocation offset for previous removals.  This
	     should not be done before calling ...symbol_deleted_p
	     because it might mess up the offset comparisons there.
	     Make sure the offset doesn't underflow in the case where
	     the first entry is removed.  */
	  if (cookie->rel->r_offset >= removed_bytes)
	    cookie->rel->r_offset -= removed_bytes;
	  else
	    cookie->rel->r_offset = 0;

	  cookie->rel++;
	}
    }

  if (removed_bytes != 0)
    {
      /* Adjust any remaining relocs (shouldn't be any).  */
      for (; cookie->rel < cookie->relend; cookie->rel++)
	{
	  if (cookie->rel->r_offset >= removed_bytes)
	    cookie->rel->r_offset -= removed_bytes;
	  else
	    cookie->rel->r_offset = 0;
	}

      /* Clear the removed bytes.  */
      memset (&contents[section_size - removed_bytes], 0, removed_bytes);

      pin_contents (sec, contents);
      pin_internal_relocs (sec, cookie->rels);

      /* Shrink size.  */
      sec->size = section_size - removed_bytes;

      if (xtensa_is_littable_section (sec))
	{
	  bfd *dynobj = elf_hash_table (info)->dynobj;
	  if (dynobj)
	    {
	      asection *sgotloc =
		bfd_get_section_by_name (dynobj, ".got.loc");
	      if (sgotloc)
		sgotloc->size -= removed_bytes;
	    }
	}
    }
  else
    {
      release_contents (sec, contents);
      release_internal_relocs (sec, cookie->rels);
    }

  return (removed_bytes != 0);
}


static bfd_boolean
elf_xtensa_discard_info (bfd *abfd,
			 struct elf_reloc_cookie *cookie,
			 struct bfd_link_info *info)
{
  asection *sec;
  bfd_boolean changed = FALSE;

  for (sec = abfd->sections; sec != NULL; sec = sec->next)
    {
      if (xtensa_is_property_section (sec))
	{
	  if (elf_xtensa_discard_info_for_section (abfd, cookie, info, sec))
	    changed = TRUE;
	}
    }

  return changed;
}


static bfd_boolean
elf_xtensa_ignore_discarded_relocs (asection *sec)
{
  return xtensa_is_property_section (sec);
}


/* Support for core dump NOTE sections.  */

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

  /* The size for Xtensa is variable, so don't try to recognize the format
     based on the size.  Just assume this is GNU/Linux.  */

  /* pr_cursig */
  elf_tdata (abfd)->core_signal = bfd_get_16 (abfd, note->descdata + 12);

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

  /* pr_reg */
  offset = 72;
  size = note->descsz - offset - 4;

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


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

      case 128:		/* GNU/Linux elf_prpsinfo */
	elf_tdata (abfd)->core_program
	 = _bfd_elfcore_strndup (abfd, note->descdata + 32, 16);
	elf_tdata (abfd)->core_command
	 = _bfd_elfcore_strndup (abfd, note->descdata + 48, 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;
}


/* Generic Xtensa configurability stuff.  */

static xtensa_opcode callx0_op = XTENSA_UNDEFINED;
static xtensa_opcode callx4_op = XTENSA_UNDEFINED;
static xtensa_opcode callx8_op = XTENSA_UNDEFINED;
static xtensa_opcode callx12_op = XTENSA_UNDEFINED;
static xtensa_opcode call0_op = XTENSA_UNDEFINED;
static xtensa_opcode call4_op = XTENSA_UNDEFINED;
static xtensa_opcode call8_op = XTENSA_UNDEFINED;
static xtensa_opcode call12_op = XTENSA_UNDEFINED;

static void
init_call_opcodes (void)
{
  if (callx0_op == XTENSA_UNDEFINED)
    {
      callx0_op  = xtensa_opcode_lookup (xtensa_default_isa, "callx0");
      callx4_op  = xtensa_opcode_lookup (xtensa_default_isa, "callx4");
      callx8_op  = xtensa_opcode_lookup (xtensa_default_isa, "callx8");
      callx12_op = xtensa_opcode_lookup (xtensa_default_isa, "callx12");
      call0_op   = xtensa_opcode_lookup (xtensa_default_isa, "call0");
      call4_op   = xtensa_opcode_lookup (xtensa_default_isa, "call4");
      call8_op   = xtensa_opcode_lookup (xtensa_default_isa, "call8");
      call12_op  = xtensa_opcode_lookup (xtensa_default_isa, "call12");
    }
}


static bfd_boolean
is_indirect_call_opcode (xtensa_opcode opcode)
{
  init_call_opcodes ();
  return (opcode == callx0_op
	  || opcode == callx4_op
	  || opcode == callx8_op
	  || opcode == callx12_op);
}


static bfd_boolean
is_direct_call_opcode (xtensa_opcode opcode)
{
  init_call_opcodes ();
  return (opcode == call0_op
	  || opcode == call4_op
	  || opcode == call8_op
	  || opcode == call12_op);
}


static bfd_boolean
is_windowed_call_opcode (xtensa_opcode opcode)
{
  init_call_opcodes ();
  return (opcode == call4_op
	  || opcode == call8_op
	  || opcode == call12_op
	  || opcode == callx4_op
	  || opcode == callx8_op
	  || opcode == callx12_op);
}


static xtensa_opcode
get_const16_opcode (void)
{
  static bfd_boolean done_lookup = FALSE;
  static xtensa_opcode const16_opcode = XTENSA_UNDEFINED;
  if (!done_lookup)
    {
      const16_opcode = xtensa_opcode_lookup (xtensa_default_isa, "const16");
      done_lookup = TRUE;
    }
  return const16_opcode;
}


static xtensa_opcode
get_l32r_opcode (void)
{
  static xtensa_opcode l32r_opcode = XTENSA_UNDEFINED;
  static bfd_boolean done_lookup = FALSE;

  if (!done_lookup)
    {
      l32r_opcode = xtensa_opcode_lookup (xtensa_default_isa, "l32r");
      done_lookup = TRUE;
    }
  return l32r_opcode;
}


static bfd_vma
l32r_offset (bfd_vma addr, bfd_vma pc)
{
  bfd_vma offset;

  offset = addr - ((pc+3) & -4);
  BFD_ASSERT ((offset & ((1 << 2) - 1)) == 0);
  offset = (signed int) offset >> 2;
  BFD_ASSERT ((signed int) offset >> 16 == -1);
  return offset;
}


static int
get_relocation_opnd (xtensa_opcode opcode, int r_type)
{
  xtensa_isa isa = xtensa_default_isa;
  int last_immed, last_opnd, opi;

  if (opcode == XTENSA_UNDEFINED)
    return XTENSA_UNDEFINED;

  /* Find the last visible PC-relative immediate operand for the opcode.
     If there are no PC-relative immediates, then choose the last visible
     immediate; otherwise, fail and return XTENSA_UNDEFINED.  */
  last_immed = XTENSA_UNDEFINED;
  last_opnd = xtensa_opcode_num_operands (isa, opcode);
  for (opi = last_opnd - 1; opi >= 0; opi--)
    {
      if (xtensa_operand_is_visible (isa, opcode, opi) == 0)
	continue;
      if (xtensa_operand_is_PCrelative (isa, opcode, opi) == 1)
	{
	  last_immed = opi;
	  break;
	}
      if (last_immed == XTENSA_UNDEFINED
	  && xtensa_operand_is_register (isa, opcode, opi) == 0)
	last_immed = opi;
    }
  if (last_immed < 0)
    return XTENSA_UNDEFINED;

  /* If the operand number was specified in an old-style relocation,
     check for consistency with the operand computed above.  */
  if (r_type >= R_XTENSA_OP0 && r_type <= R_XTENSA_OP2)
    {
      int reloc_opnd = r_type - R_XTENSA_OP0;
      if (reloc_opnd != last_immed)
	return XTENSA_UNDEFINED;
    }

  return last_immed;
}


int
get_relocation_slot (int r_type)
{
  switch (r_type)
    {
    case R_XTENSA_OP0:
    case R_XTENSA_OP1:
    case R_XTENSA_OP2:
      return 0;

    default:
      if (r_type >= R_XTENSA_SLOT0_OP && r_type <= R_XTENSA_SLOT14_OP)
	return r_type - R_XTENSA_SLOT0_OP;
      if (r_type >= R_XTENSA_SLOT0_ALT && r_type <= R_XTENSA_SLOT14_ALT)
	return r_type - R_XTENSA_SLOT0_ALT;
      break;
    }

  return XTENSA_UNDEFINED;
}


/* Get the opcode for a relocation.  */

static xtensa_opcode
get_relocation_opcode (bfd *abfd,
		       asection *sec,
		       bfd_byte *contents,
		       Elf_Internal_Rela *irel)
{
  static xtensa_insnbuf ibuff = NULL;
  static xtensa_insnbuf sbuff = NULL;
  xtensa_isa isa = xtensa_default_isa;
  xtensa_format fmt;
  int slot;

  if (contents == NULL)
    return XTENSA_UNDEFINED;

  if (bfd_get_section_limit (abfd, sec) <= irel->r_offset)
    return XTENSA_UNDEFINED;

  if (ibuff == NULL)
    {
      ibuff = xtensa_insnbuf_alloc (isa);
      sbuff = xtensa_insnbuf_alloc (isa);
    }

  /* Decode the instruction.  */
  xtensa_insnbuf_from_chars (isa, ibuff, &contents[irel->r_offset],
			     sec->size - irel->r_offset);
  fmt = xtensa_format_decode (isa, ibuff);
  slot = get_relocation_slot (ELF32_R_TYPE (irel->r_info));
  if (slot == XTENSA_UNDEFINED)
    return XTENSA_UNDEFINED;
  xtensa_format_get_slot (isa, fmt, slot, ibuff, sbuff);
  return xtensa_opcode_decode (isa, fmt, slot, sbuff);
}


bfd_boolean
is_l32r_relocation (bfd *abfd,
		    asection *sec,
		    bfd_byte *contents,
		    Elf_Internal_Rela *irel)
{
  xtensa_opcode opcode;
  if (!is_operand_relocation (ELF32_R_TYPE (irel->r_info)))
    return FALSE;
  opcode = get_relocation_opcode (abfd, sec, contents, irel);
  return (opcode == get_l32r_opcode ());
}


static bfd_size_type
get_asm_simplify_size (bfd_byte *contents,
		       bfd_size_type content_len,
		       bfd_size_type offset)
{
  bfd_size_type insnlen, size = 0;

  /* Decode the size of the next two instructions.  */
  insnlen = insn_decode_len (contents, content_len, offset);
  if (insnlen == 0)
    return 0;

  size += insnlen;
  
  insnlen = insn_decode_len (contents, content_len, offset + size);
  if (insnlen == 0)
    return 0;

  size += insnlen;
  return size;
}


bfd_boolean
is_alt_relocation (int r_type)
{
  return (r_type >= R_XTENSA_SLOT0_ALT
	  && r_type <= R_XTENSA_SLOT14_ALT);
}


bfd_boolean
is_operand_relocation (int r_type)
{
  switch (r_type)
    {
    case R_XTENSA_OP0:
    case R_XTENSA_OP1:
    case R_XTENSA_OP2:
      return TRUE;

    default:
      if (r_type >= R_XTENSA_SLOT0_OP && r_type <= R_XTENSA_SLOT14_OP)
	return TRUE;
      if (r_type >= R_XTENSA_SLOT0_ALT && r_type <= R_XTENSA_SLOT14_ALT)
	return TRUE;
      break;
    }

  return FALSE;
}

      
#define MIN_INSN_LENGTH 2

/* Return 0 if it fails to decode.  */

bfd_size_type
insn_decode_len (bfd_byte *contents,
		 bfd_size_type content_len,
		 bfd_size_type offset)
{
  int insn_len;
  xtensa_isa isa = xtensa_default_isa;
  xtensa_format fmt;
  static xtensa_insnbuf ibuff = NULL;

  if (offset + MIN_INSN_LENGTH > content_len)
    return 0;

  if (ibuff == NULL)
    ibuff = xtensa_insnbuf_alloc (isa);
  xtensa_insnbuf_from_chars (isa, ibuff, &contents[offset],
			     content_len - offset);
  fmt = xtensa_format_decode (isa, ibuff);
  if (fmt == XTENSA_UNDEFINED)
    return 0;
  insn_len = xtensa_format_length (isa, fmt);
  if (insn_len ==  XTENSA_UNDEFINED)
    return 0;
  return insn_len;
}


/* Decode the opcode for a single slot instruction.
   Return 0 if it fails to decode or the instruction is multi-slot.  */

xtensa_opcode
insn_decode_opcode (bfd_byte *contents,
		    bfd_size_type content_len,
		    bfd_size_type offset,
		    int slot)
{
  xtensa_isa isa = xtensa_default_isa;
  xtensa_format fmt;
  static xtensa_insnbuf insnbuf = NULL;
  static xtensa_insnbuf slotbuf = NULL;

  if (offset + MIN_INSN_LENGTH > content_len)
    return XTENSA_UNDEFINED;

  if (insnbuf == NULL)
    {
      insnbuf = xtensa_insnbuf_alloc (isa);
      slotbuf = xtensa_insnbuf_alloc (isa);
    }

  xtensa_insnbuf_from_chars (isa, insnbuf, &contents[offset],
			     content_len - offset);
  fmt = xtensa_format_decode (isa, insnbuf);
  if (fmt == XTENSA_UNDEFINED)
    return XTENSA_UNDEFINED;

  if (slot >= xtensa_format_num_slots (isa, fmt))
    return XTENSA_UNDEFINED;

  xtensa_format_get_slot (isa, fmt, slot, insnbuf, slotbuf);
  return xtensa_opcode_decode (isa, fmt, slot, slotbuf);
}


/* The offset is the offset in the contents.
   The address is the address of that offset.  */

static bfd_boolean
check_branch_target_aligned (bfd_byte *contents,
			     bfd_size_type content_length,
			     bfd_vma offset,
			     bfd_vma address)
{
  bfd_size_type insn_len = insn_decode_len (contents, content_length, offset);
  if (insn_len == 0)
    return FALSE;
  return check_branch_target_aligned_address (address, insn_len);
}


static bfd_boolean
check_loop_aligned (bfd_byte *contents,
		    bfd_size_type content_length,
		    bfd_vma offset,
		    bfd_vma address)
{
  bfd_size_type loop_len, insn_len;
  xtensa_opcode opcode =
    insn_decode_opcode (contents, content_length, offset, 0);
  BFD_ASSERT (opcode != XTENSA_UNDEFINED);
  if (opcode != XTENSA_UNDEFINED)
    return FALSE;
  BFD_ASSERT (xtensa_opcode_is_loop (xtensa_default_isa, opcode));
  if (!xtensa_opcode_is_loop (xtensa_default_isa, opcode))
    return FALSE;

  loop_len = insn_decode_len (contents, content_length, offset);
  BFD_ASSERT (loop_len != 0);
  if (loop_len == 0)
    return FALSE;

  insn_len = insn_decode_len (contents, content_length, offset + loop_len);
  BFD_ASSERT (insn_len != 0);
  if (insn_len == 0)
    return FALSE;

  return check_branch_target_aligned_address (address + loop_len, insn_len);
}


static bfd_boolean
check_branch_target_aligned_address (bfd_vma addr, int len)
{
  if (len == 8)
    return (addr % 8 == 0);
  return ((addr >> 2) == ((addr + len - 1) >> 2));
}


/* Instruction widening and narrowing.  */

/* When FLIX is available we need to access certain instructions only
   when they are 16-bit or 24-bit instructions.  This table caches
   information about such instructions by walking through all the
   opcodes and finding the smallest single-slot format into which each
   can be encoded.  */

static xtensa_format *op_single_fmt_table = NULL;


static void
init_op_single_format_table (void)
{
  xtensa_isa isa = xtensa_default_isa;
  xtensa_insnbuf ibuf;
  xtensa_opcode opcode;
  xtensa_format fmt;
  int num_opcodes;

  if (op_single_fmt_table)
    return;

  ibuf = xtensa_insnbuf_alloc (isa);
  num_opcodes = xtensa_isa_num_opcodes (isa);

  op_single_fmt_table = (xtensa_format *)
    bfd_malloc (sizeof (xtensa_format) * num_opcodes);
  for (opcode = 0; opcode < num_opcodes; opcode++)
    {
      op_single_fmt_table[opcode] = XTENSA_UNDEFINED;
      for (fmt = 0; fmt < xtensa_isa_num_formats (isa); fmt++)
	{
	  if (xtensa_format_num_slots (isa, fmt) == 1
	      && xtensa_opcode_encode (isa, fmt, 0, ibuf, opcode) == 0)
	    {
	      xtensa_opcode old_fmt = op_single_fmt_table[opcode];
	      int fmt_length = xtensa_format_length (isa, fmt);
	      if (old_fmt == XTENSA_UNDEFINED
		  || fmt_length < xtensa_format_length (isa, old_fmt))
		op_single_fmt_table[opcode] = fmt;
	    }
	}
    }
  xtensa_insnbuf_free (isa, ibuf);
}


static xtensa_format
get_single_format (xtensa_opcode opcode)
{
  init_op_single_format_table ();
  return op_single_fmt_table[opcode];
}


/* For the set of narrowable instructions we do NOT include the
   narrowings beqz -> beqz.n or bnez -> bnez.n because of complexities
   involved during linker relaxation that may require these to
   re-expand in some conditions.  Also, the narrowing "or" -> mov.n
   requires special case code to ensure it only works when op1 == op2.  */

struct string_pair
{
  const char *wide;
  const char *narrow;
};

struct string_pair narrowable[] =
{
  { "add", "add.n" },
  { "addi", "addi.n" },
  { "addmi", "addi.n" },
  { "l32i", "l32i.n" },
  { "movi", "movi.n" },
  { "ret", "ret.n" },
  { "retw", "retw.n" },
  { "s32i", "s32i.n" },
  { "or", "mov.n" } /* special case only when op1 == op2 */
};

struct string_pair widenable[] =
{
  { "add", "add.n" },
  { "addi", "addi.n" },
  { "addmi", "addi.n" },
  { "beqz", "beqz.n" },
  { "bnez", "bnez.n" },
  { "l32i", "l32i.n" },
  { "movi", "movi.n" },
  { "ret", "ret.n" },
  { "retw", "retw.n" },
  { "s32i", "s32i.n" },
  { "or", "mov.n" } /* special case only when op1 == op2 */
};


/* Attempt to narrow an instruction.  Return true if the narrowing is
   valid.  If the do_it parameter is non-zero, then perform the action
   in-place directly into the contents.  Otherwise, do not modify the
   contents.  The set of valid narrowing are specified by a string table
   but require some special case operand checks in some cases.  */

static bfd_boolean
narrow_instruction (bfd_byte *contents,
		    bfd_size_type content_length,
		    bfd_size_type offset,
		    bfd_boolean do_it)
{
  xtensa_opcode opcode;
  bfd_size_type insn_len, opi;
  xtensa_isa isa = xtensa_default_isa;
  xtensa_format fmt, o_fmt;

  static xtensa_insnbuf insnbuf = NULL;
  static xtensa_insnbuf slotbuf = NULL;
  static xtensa_insnbuf o_insnbuf = NULL;
  static xtensa_insnbuf o_slotbuf = NULL;

  if (insnbuf == NULL)
    {
      insnbuf = xtensa_insnbuf_alloc (isa);
      slotbuf = xtensa_insnbuf_alloc (isa);
      o_insnbuf = xtensa_insnbuf_alloc (isa);
      o_slotbuf = xtensa_insnbuf_alloc (isa);
    }

  BFD_ASSERT (offset < content_length);

  if (content_length < 2)
    return FALSE;

  /* We will hand-code a few of these for a little while.
     These have all been specified in the assembler aleady.  */
  xtensa_insnbuf_from_chars (isa, insnbuf, &contents[offset],
			     content_length - offset);
  fmt = xtensa_format_decode (isa, insnbuf);
  if (xtensa_format_num_slots (isa, fmt) != 1)
    return FALSE;

  if (xtensa_format_get_slot (isa, fmt, 0, insnbuf, slotbuf) != 0)
    return FALSE;

  opcode = xtensa_opcode_decode (isa, fmt, 0, slotbuf);
  if (opcode == XTENSA_UNDEFINED)
    return FALSE;
  insn_len = xtensa_format_length (isa, fmt);
  if (insn_len > content_length)
    return FALSE;

  for (opi = 0; opi < (sizeof (narrowable)/sizeof (struct string_pair)); ++opi)
    {
      bfd_boolean is_or = (strcmp ("or", narrowable[opi].wide) == 0);

      if (opcode == xtensa_opcode_lookup (isa, narrowable[opi].wide))
	{
	  uint32 value, newval;
	  int i, operand_count, o_operand_count;
	  xtensa_opcode o_opcode;

	  /* Address does not matter in this case.  We might need to
	     fix it to handle branches/jumps.  */
	  bfd_vma self_address = 0;

	  o_opcode = xtensa_opcode_lookup (isa, narrowable[opi].narrow);
	  if (o_opcode == XTENSA_UNDEFINED)
	    return FALSE;
	  o_fmt = get_single_format (o_opcode);
	  if (o_fmt == XTENSA_UNDEFINED)
	    return FALSE;

	  if (xtensa_format_length (isa, fmt) != 3
	      || xtensa_format_length (isa, o_fmt) != 2)
	    return FALSE;

	  xtensa_format_encode (isa, o_fmt, o_insnbuf);
	  operand_count = xtensa_opcode_num_operands (isa, opcode);
	  o_operand_count = xtensa_opcode_num_operands (isa, o_opcode);

	  if (xtensa_opcode_encode (isa, o_fmt, 0, o_slotbuf, o_opcode) != 0)
	    return FALSE;

	  if (!is_or)
	    {
	      if (xtensa_opcode_num_operands (isa, o_opcode) != operand_count)
		return FALSE;
	    }
	  else
	    {
	      uint32 rawval0, rawval1, rawval2;

	      if (o_operand_count + 1 != operand_count)
		return FALSE;
	      if (xtensa_operand_get_field (isa, opcode, 0,
					    fmt, 0, slotbuf, &rawval0) != 0)
		return FALSE;
	      if (xtensa_operand_get_field (isa, opcode, 1,
					    fmt, 0, slotbuf, &rawval1) != 0)
		return FALSE;
	      if (xtensa_operand_get_field (isa, opcode, 2,
					    fmt, 0, slotbuf, &rawval2) != 0)
		return FALSE;

	      if (rawval1 != rawval2)
		return FALSE;
	      if (rawval0 == rawval1) /* it is a nop */
		return FALSE;
	    }

	  for (i = 0; i < o_operand_count; ++i)
	    {
	      if (xtensa_operand_get_field (isa, opcode, i, fmt, 0,
					    slotbuf, &value)
		  || xtensa_operand_decode (isa, opcode, i, &value))
		return FALSE;

	      /* PC-relative branches need adjustment, but
		 the PC-rel operand will always have a relocation.  */
	      newval = value;
	      if (xtensa_operand_do_reloc (isa, o_opcode, i, &newval,
					   self_address)
		  || xtensa_operand_encode (isa, o_opcode, i, &newval)
		  || xtensa_operand_set_field (isa, o_opcode, i, o_fmt, 0,
					       o_slotbuf, newval))
		return FALSE;
	    }

	  if (xtensa_format_set_slot (isa, o_fmt, 0,
				      o_insnbuf, o_slotbuf) != 0)
	    return FALSE;

	  if (do_it)
	    xtensa_insnbuf_to_chars (isa, o_insnbuf, contents + offset,
				     content_length - offset);
	  return TRUE;
	}
    }
  return FALSE;
}


/* Attempt to widen an instruction.  Return true if the widening is
   valid.  If the do_it parameter is non-zero, then the action should
   be performed inplace into the contents.  Otherwise, do not modify
   the contents.  The set of valid widenings are specified by a string
   table but require some special case operand checks in some
   cases.  */

static bfd_boolean
widen_instruction (bfd_byte *contents,
		   bfd_size_type content_length,
		   bfd_size_type offset,
		   bfd_boolean do_it)
{
  xtensa_opcode opcode;
  bfd_size_type insn_len, opi;
  xtensa_isa isa = xtensa_default_isa;
  xtensa_format fmt, o_fmt;

  static xtensa_insnbuf insnbuf = NULL;
  static xtensa_insnbuf slotbuf = NULL;
  static xtensa_insnbuf o_insnbuf = NULL;
  static xtensa_insnbuf o_slotbuf = NULL;

  if (insnbuf == NULL)
    {
      insnbuf = xtensa_insnbuf_alloc (isa);
      slotbuf = xtensa_insnbuf_alloc (isa);
      o_insnbuf = xtensa_insnbuf_alloc (isa);
      o_slotbuf = xtensa_insnbuf_alloc (isa);
    }

  BFD_ASSERT (offset < content_length);

  if (content_length < 2)
    return FALSE;

  /* We will hand code a few of these for a little while.
     These have all been specified in the assembler aleady.  */
  xtensa_insnbuf_from_chars (isa, insnbuf, &contents[offset],
			     content_length - offset);
  fmt = xtensa_format_decode (isa, insnbuf);
  if (xtensa_format_num_slots (isa, fmt) != 1)
    return FALSE;

  if (xtensa_format_get_slot (isa, fmt, 0, insnbuf, slotbuf) != 0)
    return FALSE;

  opcode = xtensa_opcode_decode (isa, fmt, 0, slotbuf);
  if (opcode == XTENSA_UNDEFINED)
    return FALSE;
  insn_len = xtensa_format_length (isa, fmt);
  if (insn_len > content_length)
    return FALSE;

  for (opi = 0; opi < (sizeof (widenable)/sizeof (struct string_pair)); ++opi)
    {
      bfd_boolean is_or = (strcmp ("or", widenable[opi].wide) == 0);
      bfd_boolean is_branch = (strcmp ("beqz", widenable[opi].wide) == 0
			       || strcmp ("bnez", widenable[opi].wide) == 0);

      if (opcode == xtensa_opcode_lookup (isa, widenable[opi].narrow))
	{
	  uint32 value, newval;
	  int i, operand_count, o_operand_count, check_operand_count;
	  xtensa_opcode o_opcode;

	  /* Address does not matter in this case.  We might need to fix it
	     to handle branches/jumps.  */
	  bfd_vma self_address = 0;

	  o_opcode = xtensa_opcode_lookup (isa, widenable[opi].wide);
	  if (o_opcode == XTENSA_UNDEFINED)
	    return FALSE;
	  o_fmt = get_single_format (o_opcode);
	  if (o_fmt == XTENSA_UNDEFINED)
	    return FALSE;

	  if (xtensa_format_length (isa, fmt) != 2
	      || xtensa_format_length (isa, o_fmt) != 3)
	    return FALSE;

	  xtensa_format_encode (isa, o_fmt, o_insnbuf);
	  operand_count = xtensa_opcode_num_operands (isa, opcode);
	  o_operand_count = xtensa_opcode_num_operands (isa, o_opcode);
	  check_operand_count = o_operand_count;

	  if (xtensa_opcode_encode (isa, o_fmt, 0, o_slotbuf, o_opcode) != 0)
	    return FALSE;

	  if (!is_or)
	    {
	      if (xtensa_opcode_num_operands (isa, o_opcode) != operand_count)
		return FALSE;
	    }
	  else
	    {
	      uint32 rawval0, rawval1;

	      if (o_operand_count != operand_count + 1)
		return FALSE;
	      if (xtensa_operand_get_field (isa, opcode, 0,
					    fmt, 0, slotbuf, &rawval0) != 0)
		return FALSE;
	      if (xtensa_operand_get_field (isa, opcode, 1,
					    fmt, 0, slotbuf, &rawval1) != 0)
		return FALSE;
	      if (rawval0 == rawval1) /* it is a nop */
		return FALSE;
	    }
	  if (is_branch)
	    check_operand_count--;

	  for (i = 0; i < check_operand_count; ++i)
	    {
	      int new_i = i;
	      if (is_or && i == o_operand_count - 1)
		new_i = i - 1;
	      if (xtensa_operand_get_field (isa, opcode, new_i, fmt, 0,
					    slotbuf, &value)
		  || xtensa_operand_decode (isa, opcode, new_i, &value))
		return FALSE;

	      /* PC-relative branches need adjustment, but
		 the PC-rel operand will always have a relocation.  */
	      newval = value;
	      if (xtensa_operand_do_reloc (isa, o_opcode, i, &newval,
					   self_address)
		  || xtensa_operand_encode (isa, o_opcode, i, &newval)
		  || xtensa_operand_set_field (isa, o_opcode, i, o_fmt, 0,
					       o_slotbuf, newval))
		return FALSE;
	    }

	  if (xtensa_format_set_slot (isa, o_fmt, 0, o_insnbuf, o_slotbuf))
	    return FALSE;

	  if (do_it)
	    xtensa_insnbuf_to_chars (isa, o_insnbuf, contents + offset,
				     content_length - offset);
	  return TRUE;
	}
    }
  return FALSE;
}


/* Code for transforming CALLs at link-time.  */

static bfd_reloc_status_type
elf_xtensa_do_asm_simplify (bfd_byte *contents,
			    bfd_vma address,
			    bfd_vma content_length,
			    char **error_message)
{
  static xtensa_insnbuf insnbuf = NULL;
  static xtensa_insnbuf slotbuf = NULL;
  xtensa_format core_format = XTENSA_UNDEFINED;
  xtensa_opcode opcode;
  xtensa_opcode direct_call_opcode;
  xtensa_isa isa = xtensa_default_isa;
  bfd_byte *chbuf = contents + address;
  int opn;

  if (insnbuf == NULL)
    {
      insnbuf = xtensa_insnbuf_alloc (isa);
      slotbuf = xtensa_insnbuf_alloc (isa);
    }

  if (content_length < address)
    {
      *error_message = _("Attempt to convert L32R/CALLX to CALL failed");
      return bfd_reloc_other;
    }

  opcode = get_expanded_call_opcode (chbuf, content_length - address, 0);
  direct_call_opcode = swap_callx_for_call_opcode (opcode);
  if (direct_call_opcode == XTENSA_UNDEFINED)
    {
      *error_message = _("Attempt to convert L32R/CALLX to CALL failed");
      return bfd_reloc_other;
    }
  
  /* Assemble a NOP ("or a1, a1, a1") into the 0 byte offset.  */
  core_format = xtensa_format_lookup (isa, "x24");
  opcode = xtensa_opcode_lookup (isa, "or");
  xtensa_opcode_encode (isa, core_format, 0, slotbuf, opcode);
  for (opn = 0; opn < 3; opn++) 
    {
      uint32 regno = 1;
      xtensa_operand_encode (isa, opcode, opn, &regno);
      xtensa_operand_set_field (isa, opcode, opn, core_format, 0,
				slotbuf, regno);
    }
  xtensa_format_encode (isa, core_format, insnbuf);
  xtensa_format_set_slot (isa, core_format, 0, insnbuf, slotbuf);
  xtensa_insnbuf_to_chars (isa, insnbuf, chbuf, content_length - address);

  /* Assemble a CALL ("callN 0") into the 3 byte offset.  */
  xtensa_opcode_encode (isa, core_format, 0, slotbuf, direct_call_opcode);
  xtensa_operand_set_field (isa, opcode, 0, core_format, 0, slotbuf, 0);

  xtensa_format_encode (isa, core_format, insnbuf);
  xtensa_format_set_slot (isa, core_format, 0, insnbuf, slotbuf);
  xtensa_insnbuf_to_chars (isa, insnbuf, chbuf + 3,
			   content_length - address - 3);

  return bfd_reloc_ok;
}


static bfd_reloc_status_type
contract_asm_expansion (bfd_byte *contents,
			bfd_vma content_length,
			Elf_Internal_Rela *irel,
			char **error_message)
{
  bfd_reloc_status_type retval =
    elf_xtensa_do_asm_simplify (contents, irel->r_offset, content_length,
				error_message);

  if (retval != bfd_reloc_ok)
    return bfd_reloc_dangerous;

  /* Update the irel->r_offset field so that the right immediate and
     the right instruction are modified during the relocation.  */
  irel->r_offset += 3;
  irel->r_info = ELF32_R_INFO (ELF32_R_SYM (irel->r_info), R_XTENSA_SLOT0_OP);
  return bfd_reloc_ok;
}


static xtensa_opcode
swap_callx_for_call_opcode (xtensa_opcode opcode)
{
  init_call_opcodes ();

  if (opcode == callx0_op) return call0_op;
  if (opcode == callx4_op) return call4_op;
  if (opcode == callx8_op) return call8_op;
  if (opcode == callx12_op) return call12_op;

  /* Return XTENSA_UNDEFINED if the opcode is not an indirect call.  */
  return XTENSA_UNDEFINED;
}


/* Check if "buf" is pointing to a "L32R aN; CALLX aN" or "CONST16 aN;
   CONST16 aN; CALLX aN" sequence, and if so, return the CALLX opcode.
   If not, return XTENSA_UNDEFINED.  */

#define L32R_TARGET_REG_OPERAND 0
#define CONST16_TARGET_REG_OPERAND 0
#define CALLN_SOURCE_OPERAND 0

static xtensa_opcode 
get_expanded_call_opcode (bfd_byte *buf, int bufsize, bfd_boolean *p_uses_l32r)
{
  static xtensa_insnbuf insnbuf = NULL;
  static xtensa_insnbuf slotbuf = NULL;
  xtensa_format fmt;
  xtensa_opcode opcode;
  xtensa_isa isa = xtensa_default_isa;
  uint32 regno, const16_regno, call_regno;
  int offset = 0;

  if (insnbuf == NULL)
    {
      insnbuf = xtensa_insnbuf_alloc (isa);
      slotbuf = xtensa_insnbuf_alloc (isa);
    }

  xtensa_insnbuf_from_chars (isa, insnbuf, buf, bufsize);
  fmt = xtensa_format_decode (isa, insnbuf);
  if (fmt == XTENSA_UNDEFINED
      || xtensa_format_get_slot (isa, fmt, 0, insnbuf, slotbuf))
    return XTENSA_UNDEFINED;

  opcode = xtensa_opcode_decode (isa, fmt, 0, slotbuf);
  if (opcode == XTENSA_UNDEFINED)
    return XTENSA_UNDEFINED;

  if (opcode == get_l32r_opcode ())
    {
      if (p_uses_l32r)
	*p_uses_l32r = TRUE;
      if (xtensa_operand_get_field (isa, opcode, L32R_TARGET_REG_OPERAND,
				    fmt, 0, slotbuf, &regno)
	  || xtensa_operand_decode (isa, opcode, L32R_TARGET_REG_OPERAND,
				    &regno))
	return XTENSA_UNDEFINED;
    }
  else if (opcode == get_const16_opcode ())
    {
      if (p_uses_l32r)
	*p_uses_l32r = FALSE;
      if (xtensa_operand_get_field (isa, opcode, CONST16_TARGET_REG_OPERAND,
				    fmt, 0, slotbuf, &regno)
	  || xtensa_operand_decode (isa, opcode, CONST16_TARGET_REG_OPERAND,
				    &regno))
	return XTENSA_UNDEFINED;

      /* Check that the next instruction is also CONST16.  */
      offset += xtensa_format_length (isa, fmt);
      xtensa_insnbuf_from_chars (isa, insnbuf, buf + offset, bufsize - offset);
      fmt = xtensa_format_decode (isa, insnbuf);
      if (fmt == XTENSA_UNDEFINED
	  || xtensa_format_get_slot (isa, fmt, 0, insnbuf, slotbuf))
	return XTENSA_UNDEFINED;
      opcode = xtensa_opcode_decode (isa, fmt, 0, slotbuf);
      if (opcode != get_const16_opcode ())
	return XTENSA_UNDEFINED;

      if (xtensa_operand_get_field (isa, opcode, CONST16_TARGET_REG_OPERAND,
				    fmt, 0, slotbuf, &const16_regno)
	  || xtensa_operand_decode (isa, opcode, CONST16_TARGET_REG_OPERAND,
				    &const16_regno)
	  || const16_regno != regno)
	return XTENSA_UNDEFINED;
    }
  else
    return XTENSA_UNDEFINED;

  /* Next instruction should be an CALLXn with operand 0 == regno.  */
  offset += xtensa_format_length (isa, fmt);
  xtensa_insnbuf_from_chars (isa, insnbuf, buf + offset, bufsize - offset);
  fmt = xtensa_format_decode (isa, insnbuf);
  if (fmt == XTENSA_UNDEFINED
      || xtensa_format_get_slot (isa, fmt, 0, insnbuf, slotbuf))
    return XTENSA_UNDEFINED;
  opcode = xtensa_opcode_decode (isa, fmt, 0, slotbuf);
  if (opcode == XTENSA_UNDEFINED 
      || !is_indirect_call_opcode (opcode))
    return XTENSA_UNDEFINED;

  if (xtensa_operand_get_field (isa, opcode, CALLN_SOURCE_OPERAND,
				fmt, 0, slotbuf, &call_regno)
      || xtensa_operand_decode (isa, opcode, CALLN_SOURCE_OPERAND,
				&call_regno))
    return XTENSA_UNDEFINED;

  if (call_regno != regno)
    return XTENSA_UNDEFINED;

  return opcode;
}


/* Data structures used during relaxation.  */

/* r_reloc: relocation values.  */

/* Through the relaxation process, we need to keep track of the values
   that will result from evaluating relocations.  The standard ELF
   relocation structure is not sufficient for this purpose because we're
   operating on multiple input files at once, so we need to know which
   input file a relocation refers to.  The r_reloc structure thus
   records both the input file (bfd) and ELF relocation.

   For efficiency, an r_reloc also contains a "target_offset" field to
   cache the target-section-relative offset value that is represented by
   the relocation.
   
   The r_reloc also contains a virtual offset that allows multiple
   inserted literals to be placed at the same "address" with
   different offsets.  */

typedef struct r_reloc_struct r_reloc;

struct r_reloc_struct
{
  bfd *abfd;
  Elf_Internal_Rela rela;
  bfd_vma target_offset;
  bfd_vma virtual_offset;
};


/* The r_reloc structure is included by value in literal_value, but not
   every literal_value has an associated relocation -- some are simple
   constants.  In such cases, we set all the fields in the r_reloc
   struct to zero.  The r_reloc_is_const function should be used to
   detect this case.  */

static bfd_boolean
r_reloc_is_const (const r_reloc *r_rel)
{
  return (r_rel->abfd == NULL);
}


static bfd_vma
r_reloc_get_target_offset (const r_reloc *r_rel)
{
  bfd_vma target_offset;
  unsigned long r_symndx;

  BFD_ASSERT (!r_reloc_is_const (r_rel));
  r_symndx = ELF32_R_SYM (r_rel->rela.r_info);
  target_offset = get_elf_r_symndx_offset (r_rel->abfd, r_symndx);
  return (target_offset + r_rel->rela.r_addend);
}


static struct elf_link_hash_entry *
r_reloc_get_hash_entry (const r_reloc *r_rel)
{
  unsigned long r_symndx = ELF32_R_SYM (r_rel->rela.r_info);
  return get_elf_r_symndx_hash_entry (r_rel->abfd, r_symndx);
}


static asection *
r_reloc_get_section (const r_reloc *r_rel)
{
  unsigned long r_symndx = ELF32_R_SYM (r_rel->rela.r_info);
  return get_elf_r_symndx_section (r_rel->abfd, r_symndx);
}


static bfd_boolean
r_reloc_is_defined (const r_reloc *r_rel)
{
  asection *sec;
  if (r_rel == NULL)
    return FALSE;

  sec = r_reloc_get_section (r_rel);
  if (sec == bfd_abs_section_ptr
      || sec == bfd_com_section_ptr
      || sec == bfd_und_section_ptr)
    return FALSE;
  return TRUE;
}


static void
r_reloc_init (r_reloc *r_rel,
	      bfd *abfd,
	      Elf_Internal_Rela *irel,
	      bfd_byte *contents,
	      bfd_size_type content_length)
{
  int r_type;
  reloc_howto_type *howto;

  if (irel)
    {
      r_rel->rela = *irel;
      r_rel->abfd = abfd;
      r_rel->target_offset = r_reloc_get_target_offset (r_rel);
      r_rel->virtual_offset = 0;
      r_type = ELF32_R_TYPE (r_rel->rela.r_info);
      howto = &elf_howto_table[r_type];
      if (howto->partial_inplace)
	{
	  bfd_vma inplace_val;
	  BFD_ASSERT (r_rel->rela.r_offset < content_length);

	  inplace_val = bfd_get_32 (abfd, &contents[r_rel->rela.r_offset]);
	  r_rel->target_offset += inplace_val;
	}
    }
  else
    memset (r_rel, 0, sizeof (r_reloc));
}


#if DEBUG

static void
print_r_reloc (FILE *fp, const r_reloc *r_rel)
{
  if (r_reloc_is_defined (r_rel))
    {
      asection *sec = r_reloc_get_section (r_rel);
      fprintf (fp, " %s(%s + ", sec->owner->filename, sec->name);
    }
  else if (r_reloc_get_hash_entry (r_rel))
    fprintf (fp, " %s + ", r_reloc_get_hash_entry (r_rel)->root.root.string);
  else
    fprintf (fp, " ?? + ");

  fprintf_vma (fp, r_rel->target_offset);
  if (r_rel->virtual_offset)
    {
      fprintf (fp, " + ");
      fprintf_vma (fp, r_rel->virtual_offset);
    }
    
  fprintf (fp, ")");
}

#endif /* DEBUG */


/* source_reloc: relocations that reference literals.  */

/* To determine whether literals can be coalesced, we need to first
   record all the relocations that reference the literals.  The
   source_reloc structure below is used for this purpose.  The
   source_reloc entries are kept in a per-literal-section array, sorted
   by offset within the literal section (i.e., target offset).

   The source_sec and r_rel.rela.r_offset fields identify the source of
   the relocation.  The r_rel field records the relocation value, i.e.,
   the offset of the literal being referenced.  The opnd field is needed
   to determine the range of the immediate field to which the relocation
   applies, so we can determine whether another literal with the same
   value is within range.  The is_null field is true when the relocation
   is being removed (e.g., when an L32R is being removed due to a CALLX
   that is converted to a direct CALL).  */

typedef struct source_reloc_struct source_reloc;

struct source_reloc_struct
{
  asection *source_sec;
  r_reloc r_rel;
  xtensa_opcode opcode;
  int opnd;
  bfd_boolean is_null;
  bfd_boolean is_abs_literal;
};


static void
init_source_reloc (source_reloc *reloc,
		   asection *source_sec,
		   const r_reloc *r_rel,
		   xtensa_opcode opcode,
		   int opnd,
		   bfd_boolean is_abs_literal)
{
  reloc->source_sec = source_sec;
  reloc->r_rel = *r_rel;
  reloc->opcode = opcode;
  reloc->opnd = opnd;
  reloc->is_null = FALSE;
  reloc->is_abs_literal = is_abs_literal;
}


/* Find the source_reloc for a particular source offset and relocation
   type.  Note that the array is sorted by _target_ offset, so this is
   just a linear search.  */

static source_reloc *
find_source_reloc (source_reloc *src_relocs,
		   int src_count,
		   asection *sec,
		   Elf_Internal_Rela *irel)
{
  int i;

  for (i = 0; i < src_count; i++)
    {
      if (src_relocs[i].source_sec == sec
	  && src_relocs[i].r_rel.rela.r_offset == irel->r_offset
	  && (ELF32_R_TYPE (src_relocs[i].r_rel.rela.r_info)
	      == ELF32_R_TYPE (irel->r_info)))
	return &src_relocs[i];
    }

  return NULL;
}


static int
source_reloc_compare (const void *ap, const void *bp)
{
  const source_reloc *a = (const source_reloc *) ap;
  const source_reloc *b = (const source_reloc *) bp;

  if (a->r_rel.target_offset != b->r_rel.target_offset)
    return (a->r_rel.target_offset - b->r_rel.target_offset);

  /* We don't need to sort on these criteria for correctness,
     but enforcing a more strict ordering prevents unstable qsort
     from behaving differently with different implementations.
     Without the code below we get correct but different results
     on Solaris 2.7 and 2.8.  We would like to always produce the
     same results no matter the host. */

  if ((!a->is_null) - (!b->is_null))
    return ((!a->is_null) - (!b->is_null));
  return internal_reloc_compare (&a->r_rel.rela, &b->r_rel.rela);
}


/* Literal values and value hash tables.  */

/* Literals with the same value can be coalesced.  The literal_value
   structure records the value of a literal: the "r_rel" field holds the
   information from the relocation on the literal (if there is one) and
   the "value" field holds the contents of the literal word itself.

   The value_map structure records a literal value along with the
   location of a literal holding that value.  The value_map hash table
   is indexed by the literal value, so that we can quickly check if a
   particular literal value has been seen before and is thus a candidate
   for coalescing.  */

typedef struct literal_value_struct literal_value;
typedef struct value_map_struct value_map;
typedef struct value_map_hash_table_struct value_map_hash_table;

struct literal_value_struct
{
  r_reloc r_rel; 
  unsigned long value;
  bfd_boolean is_abs_literal;
};

struct value_map_struct
{
  literal_value val;			/* The literal value.  */
  r_reloc loc;				/* Location of the literal.  */
  value_map *next;
};

struct value_map_hash_table_struct
{
  unsigned bucket_count;
  value_map **buckets;
  unsigned count;
  bfd_boolean has_last_loc;
  r_reloc last_loc;
};


static void
init_literal_value (literal_value *lit,
		    const r_reloc *r_rel,
		    unsigned long value,
		    bfd_boolean is_abs_literal)
{
  lit->r_rel = *r_rel;
  lit->value = value;
  lit->is_abs_literal = is_abs_literal;
}


static bfd_boolean
literal_value_equal (const literal_value *src1,
		     const literal_value *src2,
		     bfd_boolean final_static_link)
{
  struct elf_link_hash_entry *h1, *h2;

  if (r_reloc_is_const (&src1->r_rel) != r_reloc_is_const (&src2->r_rel)) 
    return FALSE;

  if (r_reloc_is_const (&src1->r_rel))
    return (src1->value == src2->value);

  if (ELF32_R_TYPE (src1->r_rel.rela.r_info)
      != ELF32_R_TYPE (src2->r_rel.rela.r_info))
    return FALSE;

  if (src1->r_rel.target_offset != src2->r_rel.target_offset)
    return FALSE;
   
  if (src1->r_rel.virtual_offset != src2->r_rel.virtual_offset)
    return FALSE;

  if (src1->value != src2->value)
    return FALSE;
  
  /* Now check for the same section (if defined) or the same elf_hash
     (if undefined or weak).  */
  h1 = r_reloc_get_hash_entry (&src1->r_rel);
  h2 = r_reloc_get_hash_entry (&src2->r_rel);
  if (r_reloc_is_defined (&src1->r_rel)
      && (final_static_link
	  || ((!h1 || h1->root.type != bfd_link_hash_defweak)
	      && (!h2 || h2->root.type != bfd_link_hash_defweak))))
    {
      if (r_reloc_get_section (&src1->r_rel)
	  != r_reloc_get_section (&src2->r_rel))
	return FALSE;
    }
  else
    {
      /* Require that the hash entries (i.e., symbols) be identical.  */
      if (h1 != h2 || h1 == 0)
	return FALSE;
    }

  if (src1->is_abs_literal != src2->is_abs_literal)
    return FALSE;

  return TRUE;
}


/* Must be power of 2.  */
#define INITIAL_HASH_RELOC_BUCKET_COUNT 1024

static value_map_hash_table *
value_map_hash_table_init (void)
{
  value_map_hash_table *values;

  values = (value_map_hash_table *)
    bfd_zmalloc (sizeof (value_map_hash_table));
  values->bucket_count = INITIAL_HASH_RELOC_BUCKET_COUNT;
  values->count = 0;
  values->buckets = (value_map **)
    bfd_zmalloc (sizeof (value_map *) * values->bucket_count);
  if (values->buckets == NULL) 
    {
      free (values);
      return NULL;
    }
  values->has_last_loc = FALSE;

  return values;
}


static void
value_map_hash_table_delete (value_map_hash_table *table)
{
  free (table->buckets);
  free (table);
}


static unsigned
hash_bfd_vma (bfd_vma val)
{
  return (val >> 2) + (val >> 10);
}


static unsigned
literal_value_hash (const literal_value *src)
{
  unsigned hash_val;

  hash_val = hash_bfd_vma (src->value);
  if (!r_reloc_is_const (&src->r_rel))
    {
      void *sec_or_hash;

      hash_val += hash_bfd_vma (src->is_abs_literal * 1000);
      hash_val += hash_bfd_vma (src->r_rel.target_offset);
      hash_val += hash_bfd_vma (src->r_rel.virtual_offset);
  
      /* Now check for the same section and the same elf_hash.  */
      if (r_reloc_is_defined (&src->r_rel))
	sec_or_hash = r_reloc_get_section (&src->r_rel);
      else
	sec_or_hash = r_reloc_get_hash_entry (&src->r_rel);
      hash_val += hash_bfd_vma ((bfd_vma) (size_t) sec_or_hash);
    }
  return hash_val;
}


/* Check if the specified literal_value has been seen before.  */

static value_map *
value_map_get_cached_value (value_map_hash_table *map,
			    const literal_value *val,
			    bfd_boolean final_static_link)
{
  value_map *map_e;
  value_map *bucket;
  unsigned idx;

  idx = literal_value_hash (val);
  idx = idx & (map->bucket_count - 1);
  bucket = map->buckets[idx];
  for (map_e = bucket; map_e; map_e = map_e->next)
    {
      if (literal_value_equal (&map_e->val, val, final_static_link))
	return map_e;
    }
  return NULL;
}


/* Record a new literal value.  It is illegal to call this if VALUE
   already has an entry here.  */

static value_map *
add_value_map (value_map_hash_table *map,
	       const literal_value *val,
	       const r_reloc *loc,
	       bfd_boolean final_static_link)
{
  value_map **bucket_p;
  unsigned idx;

  value_map *val_e = (value_map *) bfd_zmalloc (sizeof (value_map));
  if (val_e == NULL)
    {
      bfd_set_error (bfd_error_no_memory);
      return NULL;
    }

  BFD_ASSERT (!value_map_get_cached_value (map, val, final_static_link));
  val_e->val = *val;
  val_e->loc = *loc;

  idx = literal_value_hash (val);
  idx = idx & (map->bucket_count - 1);
  bucket_p = &map->buckets[idx];

  val_e->next = *bucket_p;
  *bucket_p = val_e;
  map->count++;
  /* FIXME: Consider resizing the hash table if we get too many entries.  */
  
  return val_e;
}


/* Lists of text actions (ta_) for narrowing, widening, longcall
   conversion, space fill, code & literal removal, etc.  */

/* The following text actions are generated:

   "ta_remove_insn"         remove an instruction or instructions
   "ta_remove_longcall"     convert longcall to call
   "ta_convert_longcall"    convert longcall to nop/call
   "ta_narrow_insn"         narrow a wide instruction
   "ta_widen"               widen a narrow instruction
   "ta_fill"                add fill or remove fill
      removed < 0 is a fill; branches to the fill address will be
	changed to address + fill size (e.g., address - removed)
      removed >= 0 branches to the fill address will stay unchanged
   "ta_remove_literal"      remove a literal; this action is
			    indicated when a literal is removed
                            or replaced.
   "ta_add_literal"         insert a new literal; this action is
                            indicated when a literal has been moved.
                            It may use a virtual_offset because
			    multiple literals can be placed at the
                            same location.

   For each of these text actions, we also record the number of bytes
   removed by performing the text action.  In the case of a "ta_widen"
   or a "ta_fill" that adds space, the removed_bytes will be negative.  */

typedef struct text_action_struct text_action;
typedef struct text_action_list_struct text_action_list;
typedef enum text_action_enum_t text_action_t;

enum text_action_enum_t
{
  ta_none,
  ta_remove_insn,        /* removed = -size */
  ta_remove_longcall,    /* removed = -size */
  ta_convert_longcall,   /* removed = 0 */
  ta_narrow_insn,        /* removed = -1 */
  ta_widen_insn,         /* removed = +1 */
  ta_fill,               /* removed = +size */
  ta_remove_literal,
  ta_add_literal
};


/* Structure for a text action record.  */
struct text_action_struct
{
  text_action_t action;
  asection *sec;	/* Optional */
  bfd_vma offset;
  bfd_vma virtual_offset;  /* Zero except for adding literals.  */
  int removed_bytes;
  literal_value value;	/* Only valid when adding literals.  */

  text_action *next;
};


/* List of all of the actions taken on a text section.  */
struct text_action_list_struct
{
  text_action *head;
};


static text_action *
find_fill_action (text_action_list *l, asection *sec, bfd_vma offset)
{
  text_action **m_p;

  /* It is not necessary to fill at the end of a section.  */
  if (sec->size == offset)
    return NULL;

  for (m_p = &l->head; *m_p && (*m_p)->offset <= offset; m_p = &(*m_p)->next)
    {
      text_action *t = *m_p;
      /* When the action is another fill at the same address,
	 just increase the size.  */
      if (t->offset == offset && t->action == ta_fill)
	return t;
    }
  return NULL;
}


static int
compute_removed_action_diff (const text_action *ta,
			     asection *sec,
			     bfd_vma offset,
			     int removed,
			     int removable_space)
{
  int new_removed;
  int current_removed = 0;

  if (ta)
    current_removed = ta->removed_bytes;

  BFD_ASSERT (ta == NULL || ta->offset == offset);
  BFD_ASSERT (ta == NULL || ta->action == ta_fill);

  /* It is not necessary to fill at the end of a section.  Clean this up.  */
  if (sec->size == offset)
    new_removed = removable_space - 0;
  else
    {
      int space;
      int added = -removed - current_removed;
      /* Ignore multiples of the section alignment.  */
      added = ((1 << sec->alignment_power) - 1) & added;
      new_removed = (-added);

      /* Modify for removable.  */
      space = removable_space - new_removed;
      new_removed = (removable_space
		     - (((1 << sec->alignment_power) - 1) & space));
    }
  return (new_removed - current_removed);
}


static void
adjust_fill_action (text_action *ta, int fill_diff)
{
  ta->removed_bytes += fill_diff;
}


/* Add a modification action to the text.  For the case of adding or
   removing space, modify any current fill and assume that
   "unreachable_space" bytes can be freely contracted.  Note that a
   negative removed value is a fill.  */

static void 
text_action_add (text_action_list *l,
		 text_action_t action,
		 asection *sec,
		 bfd_vma offset,
		 int removed)
{
  text_action **m_p;
  text_action *ta;

  /* It is not necessary to fill at the end of a section.  */
  if (action == ta_fill && sec->size == offset)
    return;

  /* It is not necessary to fill 0 bytes.  */
  if (action == ta_fill && removed == 0)
    return;

  for (m_p = &l->head; *m_p && (*m_p)->offset <= offset; m_p = &(*m_p)->next)
    {
      text_action *t = *m_p;
      /* When the action is another fill at the same address,
	 just increase the size.  */
      if (t->offset == offset && t->action == ta_fill && action == ta_fill)
	{
	  t->removed_bytes += removed;
	  return;
	}
    }

  /* Create a new record and fill it up.  */
  ta = (text_action *) bfd_zmalloc (sizeof (text_action));
  ta->action = action;
  ta->sec = sec;
  ta->offset = offset;
  ta->removed_bytes = removed;
  ta->next = (*m_p);
  *m_p = ta;
}


static void
text_action_add_literal (text_action_list *l,
			 text_action_t action,
			 const r_reloc *loc,
			 const literal_value *value,
			 int removed)
{
  text_action **m_p;
  text_action *ta;
  asection *sec = r_reloc_get_section (loc);
  bfd_vma offset = loc->target_offset;
  bfd_vma virtual_offset = loc->virtual_offset;

  BFD_ASSERT (action == ta_add_literal);

  for (m_p = &l->head; *m_p != NULL; m_p = &(*m_p)->next)
    {
      if ((*m_p)->offset > offset
	  && ((*m_p)->offset != offset
	      || (*m_p)->virtual_offset > virtual_offset))
	break;
    }

  /* Create a new record and fill it up.  */
  ta = (text_action *) bfd_zmalloc (sizeof (text_action));
  ta->action = action;
  ta->sec = sec;
  ta->offset = offset;
  ta->virtual_offset = virtual_offset;
  ta->value = *value;
  ta->removed_bytes = removed;
  ta->next = (*m_p);
  *m_p = ta;
}


static bfd_vma 
offset_with_removed_text (text_action_list *action_list, bfd_vma offset)
{
  text_action *r;
  int removed = 0;

  for (r = action_list->head; r && r->offset <= offset; r = r->next)
    {
      if (r->offset < offset
	  || (r->action == ta_fill && r->removed_bytes < 0))
	removed += r->removed_bytes;
    }

  return (offset - removed);
}


static bfd_vma
offset_with_removed_text_before_fill (text_action_list *action_list,
				      bfd_vma offset)
{
  text_action *r;
  int removed = 0;

  for (r = action_list->head; r && r->offset < offset; r = r->next)
    removed += r->removed_bytes;

  return (offset - removed);
}


/* The find_insn_action routine will only find non-fill actions.  */

static text_action *
find_insn_action (text_action_list *action_list, bfd_vma offset)
{
  text_action *t;
  for (t = action_list->head; t; t = t->next)
    {
      if (t->offset == offset)
	{
	  switch (t->action)
	    {
	    case ta_none:
	    case ta_fill:
	      break;
	    case ta_remove_insn:
	    case ta_remove_longcall:
	    case ta_convert_longcall:
	    case ta_narrow_insn:
	    case ta_widen_insn:
	      return t;
	    case ta_remove_literal:
	    case ta_add_literal:
	      BFD_ASSERT (0);
	      break;
	    }
	}
    }
  return NULL;
}


#if DEBUG

static void
print_action_list (FILE *fp, text_action_list *action_list)
{
  text_action *r;

  fprintf (fp, "Text Action\n");
  for (r = action_list->head; r != NULL; r = r->next)
    {
      const char *t = "unknown";
      switch (r->action)
	{
	case ta_remove_insn:
	  t = "remove_insn"; break;
	case ta_remove_longcall:
	  t = "remove_longcall"; break;
	case ta_convert_longcall:
	  t = "remove_longcall"; break;
	case ta_narrow_insn:
	  t = "narrow_insn"; break;
	case ta_widen_insn:
	  t = "widen_insn"; break;
	case ta_fill:
	  t = "fill"; break;
	case ta_none:
	  t = "none"; break;
	case ta_remove_literal:
	  t = "remove_literal"; break;
	case ta_add_literal:
	  t = "add_literal"; break;
	}

      fprintf (fp, "%s: %s[0x%lx] \"%s\" %d\n",
	       r->sec->owner->filename,
	       r->sec->name, r->offset, t, r->removed_bytes);
    }
}

#endif /* DEBUG */


/* Lists of literals being coalesced or removed.  */

/* In the usual case, the literal identified by "from" is being
   coalesced with another literal identified by "to".  If the literal is
   unused and is being removed altogether, "to.abfd" will be NULL.
   The removed_literal entries are kept on a per-section list, sorted
   by the "from" offset field.  */

typedef struct removed_literal_struct removed_literal;
typedef struct removed_literal_list_struct removed_literal_list;

struct removed_literal_struct
{
  r_reloc from;
  r_reloc to;
  removed_literal *next;
};

struct removed_literal_list_struct
{
  removed_literal *head;
  removed_literal *tail;
};


/* Record that the literal at "from" is being removed.  If "to" is not
   NULL, the "from" literal is being coalesced with the "to" literal.  */

static void
add_removed_literal (removed_literal_list *removed_list,
		     const r_reloc *from,
		     const r_reloc *to)
{
  removed_literal *r, *new_r, *next_r;

  new_r = (removed_literal *) bfd_zmalloc (sizeof (removed_literal));

  new_r->from = *from;
  if (to)
    new_r->to = *to;
  else
    new_r->to.abfd = NULL;
  new_r->next = NULL;
  
  r = removed_list->head;
  if (r == NULL) 
    {
      removed_list->head = new_r;
      removed_list->tail = new_r;
    }
  /* Special check for common case of append.  */
  else if (removed_list->tail->from.target_offset < from->target_offset)
    {
      removed_list->tail->next = new_r;
      removed_list->tail = new_r;
    }
  else
    {
      while (r->from.target_offset < from->target_offset && r->next) 
	{
	  r = r->next;
	}
      next_r = r->next;
      r->next = new_r;
      new_r->next = next_r;
      if (next_r == NULL)
	removed_list->tail = new_r;
    }
}


/* Check if the list of removed literals contains an entry for the
   given address.  Return the entry if found.  */

static removed_literal *
find_removed_literal (removed_literal_list *removed_list, bfd_vma addr)
{
  removed_literal *r = removed_list->head;
  while (r && r->from.target_offset < addr)
    r = r->next;
  if (r && r->from.target_offset == addr)
    return r;
  return NULL;
}


#if DEBUG

static void
print_removed_literals (FILE *fp, removed_literal_list *removed_list)
{
  removed_literal *r;
  r = removed_list->head;
  if (r)
    fprintf (fp, "Removed Literals\n");
  for (; r != NULL; r = r->next)
    {
      print_r_reloc (fp, &r->from);
      fprintf (fp, " => ");
      if (r->to.abfd == NULL)
	fprintf (fp, "REMOVED");
      else
	print_r_reloc (fp, &r->to);
      fprintf (fp, "\n");
    }
}

#endif /* DEBUG */


/* Per-section data for relaxation.  */

typedef struct reloc_bfd_fix_struct reloc_bfd_fix;

struct xtensa_relax_info_struct
{
  bfd_boolean is_relaxable_literal_section;
  bfd_boolean is_relaxable_asm_section;
  int visited;				/* Number of times visited.  */

  source_reloc *src_relocs;		/* Array[src_count].  */
  int src_count;
  int src_next;				/* Next src_relocs entry to assign.  */

  removed_literal_list removed_list;
  text_action_list action_list;

  reloc_bfd_fix *fix_list;
  reloc_bfd_fix *fix_array;
  unsigned fix_array_count;

  /* Support for expanding the reloc array that is stored
     in the section structure.  If the relocations have been
     reallocated, the newly allocated relocations will be referenced
     here along with the actual size allocated.  The relocation
     count will always be found in the section structure.  */
  Elf_Internal_Rela *allocated_relocs; 
  unsigned relocs_count;
  unsigned allocated_relocs_count;
};

struct elf_xtensa_section_data
{
  struct bfd_elf_section_data elf;
  xtensa_relax_info relax_info;
};


static bfd_boolean
elf_xtensa_new_section_hook (bfd *abfd, asection *sec)
{
  struct elf_xtensa_section_data *sdata;
  bfd_size_type amt = sizeof (*sdata);

  sdata = (struct elf_xtensa_section_data *) bfd_zalloc (abfd, amt);
  if (sdata == NULL)
    return FALSE;
  sec->used_by_bfd = (void *) sdata;

  return _bfd_elf_new_section_hook (abfd, sec);
}


static xtensa_relax_info *
get_xtensa_relax_info (asection *sec)
{
  struct elf_xtensa_section_data *section_data;

  /* No info available if no section or if it is an output section.  */
  if (!sec || sec == sec->output_section)
    return NULL;

  section_data = (struct elf_xtensa_section_data *) elf_section_data (sec);
  return &section_data->relax_info;
}


static void
init_xtensa_relax_info (asection *sec)
{
  xtensa_relax_info *relax_info = get_xtensa_relax_info (sec);

  relax_info->is_relaxable_literal_section = FALSE;
  relax_info->is_relaxable_asm_section = FALSE;
  relax_info->visited = 0;

  relax_info->src_relocs = NULL;
  relax_info->src_count = 0;
  relax_info->src_next = 0;

  relax_info->removed_list.head = NULL;
  relax_info->removed_list.tail = NULL;

  relax_info->action_list.head = NULL;

  relax_info->fix_list = NULL;
  relax_info->fix_array = NULL;
  relax_info->fix_array_count = 0;

  relax_info->allocated_relocs = NULL; 
  relax_info->relocs_count = 0;
  relax_info->allocated_relocs_count = 0;
}


/* Coalescing literals may require a relocation to refer to a section in
   a different input file, but the standard relocation information
   cannot express that.  Instead, the reloc_bfd_fix structures are used
   to "fix" the relocations that refer to sections in other input files.
   These structures are kept on per-section lists.  The "src_type" field
   records the relocation type in case there are multiple relocations on
   the same location.  FIXME: This is ugly; an alternative might be to
   add new symbols with the "owner" field to some other input file.  */

struct reloc_bfd_fix_struct
{
  asection *src_sec;
  bfd_vma src_offset;
  unsigned src_type;			/* Relocation type.  */
  
  bfd *target_abfd;
  asection *target_sec;
  bfd_vma target_offset;
  bfd_boolean translated;
  
  reloc_bfd_fix *next;
};


static reloc_bfd_fix *
reloc_bfd_fix_init (asection *src_sec,
		    bfd_vma src_offset,
		    unsigned src_type,
		    bfd *target_abfd,
		    asection *target_sec,
		    bfd_vma target_offset,
		    bfd_boolean translated)
{
  reloc_bfd_fix *fix;

  fix = (reloc_bfd_fix *) bfd_malloc (sizeof (reloc_bfd_fix));
  fix->src_sec = src_sec;
  fix->src_offset = src_offset;
  fix->src_type = src_type;
  fix->target_abfd = target_abfd;
  fix->target_sec = target_sec;
  fix->target_offset = target_offset;
  fix->translated = translated;

  return fix;
}


static void
add_fix (asection *src_sec, reloc_bfd_fix *fix)
{
  xtensa_relax_info *relax_info;

  relax_info = get_xtensa_relax_info (src_sec);
  fix->next = relax_info->fix_list;
  relax_info->fix_list = fix;
}


static int
fix_compare (const void *ap, const void *bp)
{
  const reloc_bfd_fix *a = (const reloc_bfd_fix *) ap;
  const reloc_bfd_fix *b = (const reloc_bfd_fix *) bp;

  if (a->src_offset != b->src_offset)
    return (a->src_offset - b->src_offset);
  return (a->src_type - b->src_type);
}


static void
cache_fix_array (asection *sec)
{
  unsigned i, count = 0;
  reloc_bfd_fix *r;
  xtensa_relax_info *relax_info = get_xtensa_relax_info (sec);

  if (relax_info == NULL)
    return;
  if (relax_info->fix_list == NULL)
    return;

  for (r = relax_info->fix_list; r != NULL; r = r->next)
    count++;

  relax_info->fix_array =
    (reloc_bfd_fix *) bfd_malloc (sizeof (reloc_bfd_fix) * count);
  relax_info->fix_array_count = count;

  r = relax_info->fix_list;
  for (i = 0; i < count; i++, r = r->next)
    {
      relax_info->fix_array[count - 1 - i] = *r;
      relax_info->fix_array[count - 1 - i].next = NULL;
    }

  qsort (relax_info->fix_array, relax_info->fix_array_count,
	 sizeof (reloc_bfd_fix), fix_compare);
}


static reloc_bfd_fix *
get_bfd_fix (asection *sec, bfd_vma offset, unsigned type)
{
  xtensa_relax_info *relax_info = get_xtensa_relax_info (sec);
  reloc_bfd_fix *rv;
  reloc_bfd_fix key;

  if (relax_info == NULL)
    return NULL;
  if (relax_info->fix_list == NULL)
    return NULL;

  if (relax_info->fix_array == NULL)
    cache_fix_array (sec);

  key.src_offset = offset;
  key.src_type = type;
  rv = bsearch (&key, relax_info->fix_array,  relax_info->fix_array_count,
		sizeof (reloc_bfd_fix), fix_compare);
  return rv;
}


/* Section caching.  */

typedef struct section_cache_struct section_cache_t;

struct section_cache_struct
{
  asection *sec;

  bfd_byte *contents;		/* Cache of the section contents.  */
  bfd_size_type content_length;

  property_table_entry *ptbl;	/* Cache of the section property table.  */
  unsigned pte_count;

  Elf_Internal_Rela *relocs;	/* Cache of the section relocations.  */
  unsigned reloc_count;
};


static void
init_section_cache (section_cache_t *sec_cache)
{
  memset (sec_cache, 0, sizeof (*sec_cache));
}


static void
clear_section_cache (section_cache_t *sec_cache)
{
  if (sec_cache->sec)
    {
      release_contents (sec_cache->sec, sec_cache->contents);
      release_internal_relocs (sec_cache->sec, sec_cache->relocs);
      if (sec_cache->ptbl)
	free (sec_cache->ptbl);
      memset (sec_cache, 0, sizeof (sec_cache));
    }
}


static bfd_boolean
section_cache_section (section_cache_t *sec_cache,
		       asection *sec,
		       struct bfd_link_info *link_info)
{
  bfd *abfd;
  property_table_entry *prop_table = NULL;
  int ptblsize = 0;
  bfd_byte *contents = NULL;
  Elf_Internal_Rela *internal_relocs = NULL;
  bfd_size_type sec_size;

  if (sec == NULL)
    return FALSE;
  if (sec == sec_cache->sec)
    return TRUE;

  abfd = sec->owner;
  sec_size = bfd_get_section_limit (abfd, sec);

  /* Get the contents.  */
  contents = retrieve_contents (abfd, sec, link_info->keep_memory);
  if (contents == NULL && sec_size != 0)
    goto err;

  /* Get the relocations.  */
  internal_relocs = retrieve_internal_relocs (abfd, sec,
					      link_info->keep_memory);

  /* Get the entry table.  */
  ptblsize = xtensa_read_table_entries (abfd, sec, &prop_table,
					XTENSA_PROP_SEC_NAME, FALSE);
  if (ptblsize < 0)
    goto err;

  /* Fill in the new section cache.  */
  clear_section_cache (sec_cache);
  memset (sec_cache, 0, sizeof (sec_cache));

  sec_cache->sec = sec;
  sec_cache->contents = contents;
  sec_cache->content_length = sec_size;
  sec_cache->relocs = internal_relocs;
  sec_cache->reloc_count = sec->reloc_count;
  sec_cache->pte_count = ptblsize;
  sec_cache->ptbl = prop_table;

  return TRUE;

 err:
  release_contents (sec, contents);
  release_internal_relocs (sec, internal_relocs);
  if (prop_table)
    free (prop_table);
  return FALSE;
}


/* Extended basic blocks.  */

/* An ebb_struct represents an Extended Basic Block.  Within this
   range, we guarantee that all instructions are decodable, the
   property table entries are contiguous, and no property table
   specifies a segment that cannot have instructions moved.  This
   structure contains caches of the contents, property table and
   relocations for the specified section for easy use.  The range is
   specified by ranges of indices for the byte offset, property table
   offsets and relocation offsets.  These must be consistent.  */

typedef struct ebb_struct ebb_t;

struct ebb_struct
{
  asection *sec;

  bfd_byte *contents;		/* Cache of the section contents.  */
  bfd_size_type content_length;

  property_table_entry *ptbl;	/* Cache of the section property table.  */
  unsigned pte_count;

  Elf_Internal_Rela *relocs;	/* Cache of the section relocations.  */
  unsigned reloc_count;

  bfd_vma start_offset;		/* Offset in section.  */
  unsigned start_ptbl_idx;	/* Offset in the property table.  */
  unsigned start_reloc_idx;	/* Offset in the relocations.  */

  bfd_vma end_offset;
  unsigned end_ptbl_idx;
  unsigned end_reloc_idx;

  bfd_boolean ends_section;	/* Is this the last ebb in a section?  */

  /* The unreachable property table at the end of this set of blocks;
     NULL if the end is not an unreachable block.  */
  property_table_entry *ends_unreachable;
};


enum ebb_target_enum
{
  EBB_NO_ALIGN = 0,
  EBB_DESIRE_TGT_ALIGN,
  EBB_REQUIRE_TGT_ALIGN,
  EBB_REQUIRE_LOOP_ALIGN,
  EBB_REQUIRE_ALIGN
};


/* proposed_action_struct is similar to the text_action_struct except
   that is represents a potential transformation, not one that will
   occur.  We build a list of these for an extended basic block
   and use them to compute the actual actions desired.  We must be
   careful that the entire set of actual actions we perform do not
   break any relocations that would fit if the actions were not
   performed.  */

typedef struct proposed_action_struct proposed_action;

struct proposed_action_struct
{
  enum ebb_target_enum align_type; /* for the target alignment */
  bfd_vma alignment_pow;
  text_action_t action;
  bfd_vma offset;
  int removed_bytes;
  bfd_boolean do_action; /* If false, then we will not perform the action.  */
};


/* The ebb_constraint_struct keeps a set of proposed actions for an
   extended basic block.   */

typedef struct ebb_constraint_struct ebb_constraint;

struct ebb_constraint_struct
{
  ebb_t ebb;
  bfd_boolean start_movable;

  /* Bytes of extra space at the beginning if movable.  */
  int start_extra_space;

  enum ebb_target_enum start_align;

  bfd_boolean end_movable;

  /* Bytes of extra space at the end if movable.  */
  int end_extra_space;

  unsigned action_count;
  unsigned action_allocated;

  /* Array of proposed actions.  */
  proposed_action *actions;

  /* Action alignments -- one for each proposed action.  */
  enum ebb_target_enum *action_aligns;
};


static void
init_ebb_constraint (ebb_constraint *c)
{
  memset (c, 0, sizeof (ebb_constraint));
}


static void
free_ebb_constraint (ebb_constraint *c)
{
  if (c->actions)
    free (c->actions);
}


static void
init_ebb (ebb_t *ebb,
	  asection *sec,
	  bfd_byte *contents,
	  bfd_size_type content_length,
	  property_table_entry *prop_table,
	  unsigned ptblsize,
	  Elf_Internal_Rela *internal_relocs,
	  unsigned reloc_count)
{
  memset (ebb, 0, sizeof (ebb_t));
  ebb->sec = sec;
  ebb->contents = contents;
  ebb->content_length = content_length;
  ebb->ptbl = prop_table;
  ebb->pte_count = ptblsize;
  ebb->relocs = internal_relocs;
  ebb->reloc_count = reloc_count;
  ebb->start_offset = 0;
  ebb->end_offset = ebb->content_length - 1;
  ebb->start_ptbl_idx = 0;
  ebb->end_ptbl_idx = ptblsize;
  ebb->start_reloc_idx = 0;
  ebb->end_reloc_idx = reloc_count;
}


/* Extend the ebb to all decodable contiguous sections.  The algorithm
   for building a basic block around an instruction is to push it
   forward until we hit the end of a section, an unreachable block or
   a block that cannot be transformed.  Then we push it backwards
   searching for similar conditions.  */

static bfd_boolean extend_ebb_bounds_forward (ebb_t *);
static bfd_boolean extend_ebb_bounds_backward (ebb_t *);
static bfd_size_type insn_block_decodable_len
  (bfd_byte *, bfd_size_type, bfd_vma, bfd_size_type);

static bfd_boolean
extend_ebb_bounds (ebb_t *ebb)
{
  if (!extend_ebb_bounds_forward (ebb))
    return FALSE;
  if (!extend_ebb_bounds_backward (ebb))
    return FALSE;
  return TRUE;
}


static bfd_boolean
extend_ebb_bounds_forward (ebb_t *ebb)
{
  property_table_entry *the_entry, *new_entry;

  the_entry = &ebb->ptbl[ebb->end_ptbl_idx];

  /* Stop when (1) we cannot decode an instruction, (2) we are at
     the end of the property tables, (3) we hit a non-contiguous property
     table entry, (4) we hit a NO_TRANSFORM region.  */

  while (1)
    {
      bfd_vma entry_end;
      bfd_size_type insn_block_len;

      entry_end = the_entry->address - ebb->sec->vma + the_entry->size;
      insn_block_len =
	insn_block_decodable_len (ebb->contents, ebb->content_length,
				  ebb->end_offset,
				  entry_end - ebb->end_offset);
      if (insn_block_len != (entry_end - ebb->end_offset))
	{
	  (*_bfd_error_handler)
	    (_("%B(%A+0x%lx): could not decode instruction; possible configuration mismatch"),
	     ebb->sec->owner, ebb->sec, ebb->end_offset + insn_block_len);
	  return FALSE;
	}
      ebb->end_offset += insn_block_len;

      if (ebb->end_offset == ebb->sec->size)
	ebb->ends_section = TRUE;

      /* Update the reloc counter.  */
      while (ebb->end_reloc_idx + 1 < ebb->reloc_count
	     && (ebb->relocs[ebb->end_reloc_idx + 1].r_offset
		 < ebb->end_offset))
	{
	  ebb->end_reloc_idx++;
	}

      if (ebb->end_ptbl_idx + 1 == ebb->pte_count)
	return TRUE;

      new_entry = &ebb->ptbl[ebb->end_ptbl_idx + 1];
      if (((new_entry->flags & XTENSA_PROP_INSN) == 0)
	  || ((new_entry->flags & XTENSA_PROP_INSN_NO_TRANSFORM) != 0)
	  || ((the_entry->flags & XTENSA_PROP_ALIGN) != 0))
	break;

      if (the_entry->address + the_entry->size != new_entry->address)
	break;

      the_entry = new_entry;
      ebb->end_ptbl_idx++;
    }

  /* Quick check for an unreachable or end of file just at the end.  */
  if (ebb->end_ptbl_idx + 1 == ebb->pte_count)
    {
      if (ebb->end_offset == ebb->content_length)
	ebb->ends_section = TRUE;
    }
  else
    {
      new_entry = &ebb->ptbl[ebb->end_ptbl_idx + 1];
      if ((new_entry->flags & XTENSA_PROP_UNREACHABLE) != 0
	  && the_entry->address + the_entry->size == new_entry->address)
	ebb->ends_unreachable = new_entry;
    }

  /* Any other ending requires exact alignment.  */
  return TRUE;
}


static bfd_boolean
extend_ebb_bounds_backward (ebb_t *ebb)
{
  property_table_entry *the_entry, *new_entry;

  the_entry = &ebb->ptbl[ebb->start_ptbl_idx];

  /* Stop when (1) we cannot decode the instructions in the current entry.
     (2) we are at the beginning of the property tables, (3) we hit a
     non-contiguous property table entry, (4) we hit a NO_TRANSFORM region.  */

  while (1)
    {
      bfd_vma block_begin;
      bfd_size_type insn_block_len;

      block_begin = the_entry->address - ebb->sec->vma;
      insn_block_len =
	insn_block_decodable_len (ebb->contents, ebb->content_length,
				  block_begin,
				  ebb->start_offset - block_begin);
      if (insn_block_len != ebb->start_offset - block_begin)
	{
	  (*_bfd_error_handler)
	    (_("%B(%A+0x%lx): could not decode instruction; possible configuration mismatch"),
	     ebb->sec->owner, ebb->sec, ebb->end_offset + insn_block_len);
	  return FALSE;
	}
      ebb->start_offset -= insn_block_len;

      /* Update the reloc counter.  */
      while (ebb->start_reloc_idx > 0
	     && (ebb->relocs[ebb->start_reloc_idx - 1].r_offset
		 >= ebb->start_offset))
	{
	  ebb->start_reloc_idx--;
	}

      if (ebb->start_ptbl_idx == 0)
	return TRUE;

      new_entry = &ebb->ptbl[ebb->start_ptbl_idx - 1];
      if ((new_entry->flags & XTENSA_PROP_INSN) == 0
	  || ((new_entry->flags & XTENSA_PROP_INSN_NO_TRANSFORM) != 0)
	  || ((new_entry->flags & XTENSA_PROP_ALIGN) != 0))
	return TRUE;
      if (new_entry->address + new_entry->size != the_entry->address)
	return TRUE;

      the_entry = new_entry;
      ebb->start_ptbl_idx--;
    }
  return TRUE;
}


static bfd_size_type
insn_block_decodable_len (bfd_byte *contents,
			  bfd_size_type content_len,
			  bfd_vma block_offset,
			  bfd_size_type block_len)
{
  bfd_vma offset = block_offset;

  while (offset < block_offset + block_len)
    {
      bfd_size_type insn_len = 0;

      insn_len = insn_decode_len (contents, content_len, offset);
      if (insn_len == 0)
	return (offset - block_offset);
      offset += insn_len;
    }
  return (offset - block_offset);
}


static void
ebb_propose_action (ebb_constraint *c,
		    enum ebb_target_enum align_type,
		    bfd_vma alignment_pow,
		    text_action_t action,
		    bfd_vma offset,
		    int removed_bytes,
		    bfd_boolean do_action)
{
  proposed_action *act;

  if (c->action_allocated <= c->action_count)
    {
      unsigned new_allocated, i;
      proposed_action *new_actions;

      new_allocated = (c->action_count + 2) * 2;
      new_actions = (proposed_action *)
	bfd_zmalloc (sizeof (proposed_action) * new_allocated);

      for (i = 0; i < c->action_count; i++)
	new_actions[i] = c->actions[i];
      if (c->actions)
	free (c->actions);
      c->actions = new_actions;
      c->action_allocated = new_allocated;
    }

  act = &c->actions[c->action_count];
  act->align_type = align_type;
  act->alignment_pow = alignment_pow;
  act->action = action;
  act->offset = offset;
  act->removed_bytes = removed_bytes;
  act->do_action = do_action;

  c->action_count++;
}


/* Access to internal relocations, section contents and symbols.  */

/* During relaxation, we need to modify relocations, section contents,
   and symbol definitions, and we need to keep the original values from
   being reloaded from the input files, i.e., we need to "pin" the
   modified values in memory.  We also want to continue to observe the
   setting of the "keep-memory" flag.  The following functions wrap the
   standard BFD functions to take care of this for us.  */

static Elf_Internal_Rela *
retrieve_internal_relocs (bfd *abfd, asection *sec, bfd_boolean keep_memory)
{
  Elf_Internal_Rela *internal_relocs;

  if ((sec->flags & SEC_LINKER_CREATED) != 0)
    return NULL;

  internal_relocs = elf_section_data (sec)->relocs;
  if (internal_relocs == NULL)
    internal_relocs = (_bfd_elf_link_read_relocs
		       (abfd, sec, NULL, NULL, keep_memory));
  return internal_relocs;
}


static void
pin_internal_relocs (asection *sec, Elf_Internal_Rela *internal_relocs)
{
  elf_section_data (sec)->relocs = internal_relocs;
}


static void
release_internal_relocs (asection *sec, Elf_Internal_Rela *internal_relocs)
{
  if (internal_relocs
      && elf_section_data (sec)->relocs != internal_relocs)
    free (internal_relocs);
}


static bfd_byte *
retrieve_contents (bfd *abfd, asection *sec, bfd_boolean keep_memory)
{
  bfd_byte *contents;
  bfd_size_type sec_size;

  sec_size = bfd_get_section_limit (abfd, sec);
  contents = elf_section_data (sec)->this_hdr.contents;
  
  if (contents == NULL && sec_size != 0)
    {
      if (!bfd_malloc_and_get_section (abfd, sec, &contents))
	{
	  if (contents)
	    free (contents);
	  return NULL;
	}
      if (keep_memory) 
	elf_section_data (sec)->this_hdr.contents = contents;
    }
  return contents;
}


static void
pin_contents (asection *sec, bfd_byte *contents)
{
  elf_section_data (sec)->this_hdr.contents = contents;
}


static void
release_contents (asection *sec, bfd_byte *contents)
{
  if (contents && elf_section_data (sec)->this_hdr.contents != contents)
    free (contents);
}


static Elf_Internal_Sym *
retrieve_local_syms (bfd *input_bfd)
{
  Elf_Internal_Shdr *symtab_hdr;
  Elf_Internal_Sym *isymbuf;
  size_t locsymcount;

  symtab_hdr = &elf_tdata (input_bfd)->symtab_hdr;
  locsymcount = symtab_hdr->sh_info;

  isymbuf = (Elf_Internal_Sym *) symtab_hdr->contents;
  if (isymbuf == NULL && locsymcount != 0)
    isymbuf = bfd_elf_get_elf_syms (input_bfd, symtab_hdr, locsymcount, 0,
				    NULL, NULL, NULL);

  /* Save the symbols for this input file so they won't be read again.  */
  if (isymbuf && isymbuf != (Elf_Internal_Sym *) symtab_hdr->contents)
    symtab_hdr->contents = (unsigned char *) isymbuf;

  return isymbuf;
}


/* Code for link-time relaxation.  */

/* Initialization for relaxation: */
static bfd_boolean analyze_relocations (struct bfd_link_info *);
static bfd_boolean find_relaxable_sections
  (bfd *, asection *, struct bfd_link_info *, bfd_boolean *);
static bfd_boolean collect_source_relocs
  (bfd *, asection *, struct bfd_link_info *);
static bfd_boolean is_resolvable_asm_expansion
  (bfd *, asection *, bfd_byte *, Elf_Internal_Rela *, struct bfd_link_info *,
   bfd_boolean *);
static Elf_Internal_Rela *find_associated_l32r_irel
  (bfd *, asection *, bfd_byte *, Elf_Internal_Rela *, Elf_Internal_Rela *);
static bfd_boolean compute_text_actions
  (bfd *, asection *, struct bfd_link_info *);
static bfd_boolean compute_ebb_proposed_actions (ebb_constraint *);
static bfd_boolean compute_ebb_actions (ebb_constraint *);
static bfd_boolean check_section_ebb_pcrels_fit
  (bfd *, asection *, bfd_byte *, Elf_Internal_Rela *, const ebb_constraint *);
static bfd_boolean check_section_ebb_reduces (const ebb_constraint *);
static void text_action_add_proposed
  (text_action_list *, const ebb_constraint *, asection *);
static int compute_fill_extra_space (property_table_entry *);

/* First pass: */
static bfd_boolean compute_removed_literals
  (bfd *, asection *, struct bfd_link_info *, value_map_hash_table *);
static Elf_Internal_Rela *get_irel_at_offset
  (asection *, Elf_Internal_Rela *, bfd_vma);
static bfd_boolean is_removable_literal 
  (const source_reloc *, int, const source_reloc *, int);
static bfd_boolean remove_dead_literal
  (bfd *, asection *, struct bfd_link_info *, Elf_Internal_Rela *,
   Elf_Internal_Rela *, source_reloc *, property_table_entry *, int); 
static bfd_boolean identify_literal_placement
  (bfd *, asection *, bfd_byte *, struct bfd_link_info *,
   value_map_hash_table *, bfd_boolean *, Elf_Internal_Rela *, int,
   source_reloc *, property_table_entry *, int, section_cache_t *,
   bfd_boolean);
static bfd_boolean relocations_reach (source_reloc *, int, const r_reloc *);
static bfd_boolean coalesce_shared_literal
  (asection *, source_reloc *, property_table_entry *, int, value_map *);
static bfd_boolean move_shared_literal
  (asection *, struct bfd_link_info *, source_reloc *, property_table_entry *,
   int, const r_reloc *, const literal_value *, section_cache_t *);

/* Second pass: */
static bfd_boolean relax_section (bfd *, asection *, struct bfd_link_info *);
static bfd_boolean translate_section_fixes (asection *);
static bfd_boolean translate_reloc_bfd_fix (reloc_bfd_fix *);
static void translate_reloc (const r_reloc *, r_reloc *);
static void shrink_dynamic_reloc_sections
  (struct bfd_link_info *, bfd *, asection *, Elf_Internal_Rela *);
static bfd_boolean move_literal
  (bfd *, struct bfd_link_info *, asection *, bfd_vma, bfd_byte *,
   xtensa_relax_info *, Elf_Internal_Rela **, const literal_value *);
static bfd_boolean relax_property_section
  (bfd *, asection *, struct bfd_link_info *);

/* Third pass: */
static bfd_boolean relax_section_symbols (bfd *, asection *);


static bfd_boolean 
elf_xtensa_relax_section (bfd *abfd,
			  asection *sec,
			  struct bfd_link_info *link_info,
			  bfd_boolean *again)
{
  static value_map_hash_table *values = NULL;
  static bfd_boolean relocations_analyzed = FALSE;
  xtensa_relax_info *relax_info;

  if (!relocations_analyzed)
    {
      /* Do some overall initialization for relaxation.  */
      values = value_map_hash_table_init ();
      if (values == NULL)
	return FALSE;
      relaxing_section = TRUE;
      if (!analyze_relocations (link_info))
	return FALSE;
      relocations_analyzed = TRUE;
    }
  *again = FALSE;

  /* Don't mess with linker-created sections.  */
  if ((sec->flags & SEC_LINKER_CREATED) != 0)
    return TRUE;

  relax_info = get_xtensa_relax_info (sec);
  BFD_ASSERT (relax_info != NULL);

  switch (relax_info->visited)
    {
    case 0:
      /* Note: It would be nice to fold this pass into
	 analyze_relocations, but it is important for this step that the
	 sections be examined in link order.  */
      if (!compute_removed_literals (abfd, sec, link_info, values))
	return FALSE;
      *again = TRUE;
      break;

    case 1:
      if (values)
	value_map_hash_table_delete (values);
      values = NULL;
      if (!relax_section (abfd, sec, link_info))
	return FALSE;
      *again = TRUE;
      break;

    case 2:
      if (!relax_section_symbols (abfd, sec))
	return FALSE;
      break;
    }

  relax_info->visited++;
  return TRUE;
}


/* Initialization for relaxation.  */

/* This function is called once at the start of relaxation.  It scans
   all the input sections and marks the ones that are relaxable (i.e.,
   literal sections with L32R relocations against them), and then
   collects source_reloc information for all the relocations against
   those relaxable sections.  During this process, it also detects
   longcalls, i.e., calls relaxed by the assembler into indirect
   calls, that can be optimized back into direct calls.  Within each
   extended basic block (ebb) containing an optimized longcall, it
   computes a set of "text actions" that can be performed to remove
   the L32R associated with the longcall while optionally preserving
   branch target alignments.  */

static bfd_boolean
analyze_relocations (struct bfd_link_info *link_info)
{
  bfd *abfd;
  asection *sec;
  bfd_boolean is_relaxable = FALSE;

  /* Initialize the per-section relaxation info.  */
  for (abfd = link_info->input_bfds; abfd != NULL; abfd = abfd->link_next)
    for (sec = abfd->sections; sec != NULL; sec = sec->next)
      {
	init_xtensa_relax_info (sec);
      }

  /* Mark relaxable sections (and count relocations against each one).  */
  for (abfd = link_info->input_bfds; abfd != NULL; abfd = abfd->link_next)
    for (sec = abfd->sections; sec != NULL; sec = sec->next)
      {
	if (!find_relaxable_sections (abfd, sec, link_info, &is_relaxable))
	  return FALSE;
      }

  /* Bail out if there are no relaxable sections.  */
  if (!is_relaxable)
    return TRUE;

  /* Allocate space for source_relocs.  */
  for (abfd = link_info->input_bfds; abfd != NULL; abfd = abfd->link_next)
    for (sec = abfd->sections; sec != NULL; sec = sec->next)
      {
	xtensa_relax_info *relax_info;

	relax_info = get_xtensa_relax_info (sec);
	if (relax_info->is_relaxable_literal_section
	    || relax_info->is_relaxable_asm_section)
	  {
	    relax_info->src_relocs = (source_reloc *)
	      bfd_malloc (relax_info->src_count * sizeof (source_reloc));
	  }
      }

  /* Collect info on relocations against each relaxable section.  */
  for (abfd = link_info->input_bfds; abfd != NULL; abfd = abfd->link_next)
    for (sec = abfd->sections; sec != NULL; sec = sec->next)
      {
	if (!collect_source_relocs (abfd, sec, link_info))
	  return FALSE;
      }

  /* Compute the text actions.  */
  for (abfd = link_info->input_bfds; abfd != NULL; abfd = abfd->link_next)
    for (sec = abfd->sections; sec != NULL; sec = sec->next)
      {
	if (!compute_text_actions (abfd, sec, link_info))
	  return FALSE;
      }

  return TRUE;
}


/* Find all the sections that might be relaxed.  The motivation for
   this pass is that collect_source_relocs() needs to record _all_ the
   relocations that target each relaxable section.  That is expensive
   and unnecessary unless the target section is actually going to be
   relaxed.  This pass identifies all such sections by checking if
   they have L32Rs pointing to them.  In the process, the total number
   of relocations targeting each section is also counted so that we
   know how much space to allocate for source_relocs against each
   relaxable literal section.  */

static bfd_boolean
find_relaxable_sections (bfd *abfd,
			 asection *sec,
			 struct bfd_link_info *link_info,
			 bfd_boolean *is_relaxable_p)
{
  Elf_Internal_Rela *internal_relocs;
  bfd_byte *contents;
  bfd_boolean ok = TRUE;
  unsigned i;
  xtensa_relax_info *source_relax_info;

  internal_relocs = retrieve_internal_relocs (abfd, sec,
					      link_info->keep_memory);
  if (internal_relocs == NULL) 
    return ok;

  contents = retrieve_contents (abfd, sec, link_info->keep_memory);
  if (contents == NULL && sec->size != 0)
    {
      ok = FALSE;
      goto error_return;
    }

  source_relax_info = get_xtensa_relax_info (sec);
  for (i = 0; i < sec->reloc_count; i++) 
    {
      Elf_Internal_Rela *irel = &internal_relocs[i];
      r_reloc r_rel;
      asection *target_sec;
      xtensa_relax_info *target_relax_info;

      /* If this section has not already been marked as "relaxable", and
	 if it contains any ASM_EXPAND relocations (marking expanded
	 longcalls) that can be optimized into direct calls, then mark
	 the section as "relaxable".  */
      if (source_relax_info
	  && !source_relax_info->is_relaxable_asm_section
	  && ELF32_R_TYPE (irel->r_info) == R_XTENSA_ASM_EXPAND)
	{
	  bfd_boolean is_reachable = FALSE;
	  if (is_resolvable_asm_expansion (abfd, sec, contents, irel,
					   link_info, &is_reachable)
	      && is_reachable)
	    {
	      source_relax_info->is_relaxable_asm_section = TRUE;
	      *is_relaxable_p = TRUE;
	    }
	}

      r_reloc_init (&r_rel, abfd, irel, contents,
		    bfd_get_section_limit (abfd, sec));

      target_sec = r_reloc_get_section (&r_rel);
      target_relax_info = get_xtensa_relax_info (target_sec);
      if (!target_relax_info)
	continue;

      /* Count PC-relative operand relocations against the target section.
         Note: The conditions tested here must match the conditions under
	 which init_source_reloc is called in collect_source_relocs().  */
      if (is_operand_relocation (ELF32_R_TYPE (irel->r_info))
	  && (!is_alt_relocation (ELF32_R_TYPE (irel->r_info))
	      || is_l32r_relocation (abfd, sec, contents, irel)))
	target_relax_info->src_count++;

      if (is_l32r_relocation (abfd, sec, contents, irel)
	  && r_reloc_is_defined (&r_rel))
	{
	  /* Mark the target section as relaxable.  */
	  target_relax_info->is_relaxable_literal_section = TRUE;
	  *is_relaxable_p = TRUE;
	}
    }

 error_return:
  release_contents (sec, contents);
  release_internal_relocs (sec, internal_relocs);
  return ok;
}


/* Record _all_ the relocations that point to relaxable sections, and
   get rid of ASM_EXPAND relocs by either converting them to
   ASM_SIMPLIFY or by removing them.  */

static bfd_boolean
collect_source_relocs (bfd *abfd,
		       asection *sec,
		       struct bfd_link_info *link_info)
{
  Elf_Internal_Rela *internal_relocs;
  bfd_byte *contents;
  bfd_boolean ok = TRUE;
  unsigned i;
  bfd_size_type sec_size;

  internal_relocs = retrieve_internal_relocs (abfd, sec, 
					      link_info->keep_memory);
  if (internal_relocs == NULL) 
    return ok;

  sec_size = bfd_get_section_limit (abfd, sec);
  contents = retrieve_contents (abfd, sec, link_info->keep_memory);
  if (contents == NULL && sec_size != 0)
    {
      ok = FALSE;
      goto error_return;
    }

  /* Record relocations against relaxable literal sections.  */
  for (i = 0; i < sec->reloc_count; i++) 
    {
      Elf_Internal_Rela *irel = &internal_relocs[i];
      r_reloc r_rel;
      asection *target_sec;
      xtensa_relax_info *target_relax_info;

      r_reloc_init (&r_rel, abfd, irel, contents, sec_size);

      target_sec = r_reloc_get_section (&r_rel);
      target_relax_info = get_xtensa_relax_info (target_sec);

      if (target_relax_info
	  && (target_relax_info->is_relaxable_literal_section
	      || target_relax_info->is_relaxable_asm_section))
	{
	  xtensa_opcode opcode = XTENSA_UNDEFINED;
	  int opnd = -1;
	  bfd_boolean is_abs_literal = FALSE;

	  if (is_alt_relocation (ELF32_R_TYPE (irel->r_info)))
	    {
	      /* None of the current alternate relocs are PC-relative,
		 and only PC-relative relocs matter here.  However, we
		 still need to record the opcode for literal
		 coalescing.  */
	      opcode = get_relocation_opcode (abfd, sec, contents, irel);
	      if (opcode == get_l32r_opcode ())
		{
		  is_abs_literal = TRUE;
		  opnd = 1;
		}
	      else
		opcode = XTENSA_UNDEFINED;
	    }
	  else if (is_operand_relocation (ELF32_R_TYPE (irel->r_info)))
	    {
	      opcode = get_relocation_opcode (abfd, sec, contents, irel);
	      opnd = get_relocation_opnd (opcode, ELF32_R_TYPE (irel->r_info));
	    }

	  if (opcode != XTENSA_UNDEFINED)
	    {
	      int src_next = target_relax_info->src_next++;
	      source_reloc *s_reloc = &target_relax_info->src_relocs[src_next];

	      init_source_reloc (s_reloc, sec, &r_rel, opcode, opnd,
				 is_abs_literal);
	    }
	}
    }

  /* Now get rid of ASM_EXPAND relocations.  At this point, the
     src_relocs array for the target literal section may still be
     incomplete, but it must at least contain the entries for the L32R
     relocations associated with ASM_EXPANDs because they were just
     added in the preceding loop over the relocations.  */

  for (i = 0; i < sec->reloc_count; i++) 
    {
      Elf_Internal_Rela *irel = &internal_relocs[i];
      bfd_boolean is_reachable;

      if (!is_resolvable_asm_expansion (abfd, sec, contents, irel, link_info,
					&is_reachable))
	continue;

      if (is_reachable)
	{
	  Elf_Internal_Rela *l32r_irel;
	  r_reloc r_rel;
	  asection *target_sec;
	  xtensa_relax_info *target_relax_info;

	  /* Mark the source_reloc for the L32R so that it will be
	     removed in compute_removed_literals(), along with the
	     associated literal.  */
	  l32r_irel = find_associated_l32r_irel (abfd, sec, contents,
						 irel, internal_relocs);
	  if (l32r_irel == NULL)
	    continue;

	  r_reloc_init (&r_rel, abfd, l32r_irel, contents, sec_size);

	  target_sec = r_reloc_get_section (&r_rel);
	  target_relax_info = get_xtensa_relax_info (target_sec);

	  if (target_relax_info
	      && (target_relax_info->is_relaxable_literal_section
		  || target_relax_info->is_relaxable_asm_section))
	    {
	      source_reloc *s_reloc;

	      /* Search the source_relocs for the entry corresponding to
		 the l32r_irel.  Note: The src_relocs array is not yet
		 sorted, but it wouldn't matter anyway because we're
		 searching by source offset instead of target offset.  */
	      s_reloc = find_source_reloc (target_relax_info->src_relocs, 
					   target_relax_info->src_next,
					   sec, l32r_irel);
	      BFD_ASSERT (s_reloc);
	      s_reloc->is_null = TRUE;
	    }

	  /* Convert this reloc to ASM_SIMPLIFY.  */
	  irel->r_info = ELF32_R_INFO (ELF32_R_SYM (irel->r_info),
				       R_XTENSA_ASM_SIMPLIFY);
	  l32r_irel->r_info = ELF32_R_INFO (0, R_XTENSA_NONE);

	  pin_internal_relocs (sec, internal_relocs);
	}
      else
	{
	  /* It is resolvable but doesn't reach.  We resolve now
	     by eliminating the relocation -- the call will remain
	     expanded into L32R/CALLX.  */
	  irel->r_info = ELF32_R_INFO (0, R_XTENSA_NONE);
	  pin_internal_relocs (sec, internal_relocs);
	}
    }

 error_return:
  release_contents (sec, contents);
  release_internal_relocs (sec, internal_relocs);
  return ok;
}


/* Return TRUE if the asm expansion can be resolved.  Generally it can
   be resolved on a final link or when a partial link locates it in the
   same section as the target.  Set "is_reachable" flag if the target of
   the call is within the range of a direct call, given the current VMA
   for this section and the target section.  */

bfd_boolean
is_resolvable_asm_expansion (bfd *abfd,
			     asection *sec,
			     bfd_byte *contents,
			     Elf_Internal_Rela *irel,
			     struct bfd_link_info *link_info,
			     bfd_boolean *is_reachable_p)
{
  asection *target_sec;
  bfd_vma target_offset;
  r_reloc r_rel;
  xtensa_opcode opcode, direct_call_opcode;
  bfd_vma self_address;
  bfd_vma dest_address;
  bfd_boolean uses_l32r;
  bfd_size_type sec_size;

  *is_reachable_p = FALSE;

  if (contents == NULL)
    return FALSE;

  if (ELF32_R_TYPE (irel->r_info) != R_XTENSA_ASM_EXPAND) 
    return FALSE;

  sec_size = bfd_get_section_limit (abfd, sec);
  opcode = get_expanded_call_opcode (contents + irel->r_offset,
				     sec_size - irel->r_offset, &uses_l32r);
  /* Optimization of longcalls that use CONST16 is not yet implemented.  */
  if (!uses_l32r)
    return FALSE;
  
  direct_call_opcode = swap_callx_for_call_opcode (opcode);
  if (direct_call_opcode == XTENSA_UNDEFINED)
    return FALSE;

  /* Check and see that the target resolves.  */
  r_reloc_init (&r_rel, abfd, irel, contents, sec_size);
  if (!r_reloc_is_defined (&r_rel))
    return FALSE;

  target_sec = r_reloc_get_section (&r_rel);
  target_offset = r_rel.target_offset;

  /* If the target is in a shared library, then it doesn't reach.  This
     isn't supposed to come up because the compiler should never generate
     non-PIC calls on systems that use shared libraries, but the linker
     shouldn't crash regardless.  */
  if (!target_sec->output_section)
    return FALSE;
      
  /* For relocatable sections, we can only simplify when the output
     section of the target is the same as the output section of the
     source.  */
  if (link_info->relocatable
      && (target_sec->output_section != sec->output_section
	  || is_reloc_sym_weak (abfd, irel)))
    return FALSE;

  self_address = (sec->output_section->vma
		  + sec->output_offset + irel->r_offset + 3);
  dest_address = (target_sec->output_section->vma
		  + target_sec->output_offset + target_offset);
      
  *is_reachable_p = pcrel_reloc_fits (direct_call_opcode, 0,
				      self_address, dest_address);

  if ((self_address >> CALL_SEGMENT_BITS) !=
      (dest_address >> CALL_SEGMENT_BITS))
    return FALSE;

  return TRUE;
}


static Elf_Internal_Rela *
find_associated_l32r_irel (bfd *abfd,
			   asection *sec,
			   bfd_byte *contents,
			   Elf_Internal_Rela *other_irel,
			   Elf_Internal_Rela *internal_relocs)
{
  unsigned i;

  for (i = 0; i < sec->reloc_count; i++) 
    {
      Elf_Internal_Rela *irel = &internal_relocs[i];

      if (irel == other_irel)
	continue;
      if (irel->r_offset != other_irel->r_offset)
	continue;
      if (is_l32r_relocation (abfd, sec, contents, irel))
	return irel;
    }

  return NULL;
}


/* The compute_text_actions function will build a list of potential
   transformation actions for code in the extended basic block of each
   longcall that is optimized to a direct call.  From this list we
   generate a set of actions to actually perform that optimizes for
   space and, if not using size_opt, maintains branch target
   alignments.

   These actions to be performed are placed on a per-section list.
   The actual changes are performed by relax_section() in the second
   pass.  */

bfd_boolean
compute_text_actions (bfd *abfd,
		      asection *sec,
		      struct bfd_link_info *link_info)
{
  xtensa_relax_info *relax_info;
  bfd_byte *contents;
  Elf_Internal_Rela *internal_relocs;
  bfd_boolean ok = TRUE;
  unsigned i;
  property_table_entry *prop_table = 0;
  int ptblsize = 0;
  bfd_size_type sec_size;
  static bfd_boolean no_insn_move = FALSE;

  if (no_insn_move)
    return ok;

  /* Do nothing if the section contains no optimized longcalls.  */
  relax_info = get_xtensa_relax_info (sec);
  BFD_ASSERT (relax_info);
  if (!relax_info->is_relaxable_asm_section)
    return ok;

  internal_relocs = retrieve_internal_relocs (abfd, sec,
					      link_info->keep_memory);

  if (internal_relocs)
    qsort (internal_relocs, sec->reloc_count, sizeof (Elf_Internal_Rela),
	   internal_reloc_compare);

  sec_size = bfd_get_section_limit (abfd, sec);
  contents = retrieve_contents (abfd, sec, link_info->keep_memory);
  if (contents == NULL && sec_size != 0)
    {
      ok = FALSE;
      goto error_return;
    }

  ptblsize = xtensa_read_table_entries (abfd, sec, &prop_table,
					XTENSA_PROP_SEC_NAME, FALSE);
  if (ptblsize < 0)
    {
      ok = FALSE;
      goto error_return;
    }

  for (i = 0; i < sec->reloc_count; i++)
    {
      Elf_Internal_Rela *irel = &internal_relocs[i];
      bfd_vma r_offset;
      property_table_entry *the_entry;
      int ptbl_idx;
      ebb_t *ebb;
      ebb_constraint ebb_table;
      bfd_size_type simplify_size;

      if (irel && ELF32_R_TYPE (irel->r_info) != R_XTENSA_ASM_SIMPLIFY)
	continue;
      r_offset = irel->r_offset;

      simplify_size = get_asm_simplify_size (contents, sec_size, r_offset);
      if (simplify_size == 0)
	{
	  (*_bfd_error_handler)
	    (_("%B(%A+0x%lx): could not decode instruction for XTENSA_ASM_SIMPLIFY relocation; possible configuration mismatch"),
	     sec->owner, sec, r_offset);
	  continue;
	}

      /* If the instruction table is not around, then don't do this
	 relaxation.  */
      the_entry = elf_xtensa_find_property_entry (prop_table, ptblsize,
						  sec->vma + irel->r_offset);
      if (the_entry == NULL || XTENSA_NO_NOP_REMOVAL)
	{
	  text_action_add (&relax_info->action_list,
			   ta_convert_longcall, sec, r_offset,
			   0);
	  continue;
	}

      /* If the next longcall happens to be at the same address as an
	 unreachable section of size 0, then skip forward.  */
      ptbl_idx = the_entry - prop_table;
      while ((the_entry->flags & XTENSA_PROP_UNREACHABLE)
	     && the_entry->size == 0
	     && ptbl_idx + 1 < ptblsize
	     && (prop_table[ptbl_idx + 1].address
		 == prop_table[ptbl_idx].address))
	{
	  ptbl_idx++;
	  the_entry++;
	}

      if (the_entry->flags & XTENSA_PROP_INSN_NO_TRANSFORM)
	  /* NO_REORDER is OK */
	continue;

      init_ebb_constraint (&ebb_table);
      ebb = &ebb_table.ebb;
      init_ebb (ebb, sec, contents, sec_size, prop_table, ptblsize,
		internal_relocs, sec->reloc_count);
      ebb->start_offset = r_offset + simplify_size;
      ebb->end_offset = r_offset + simplify_size;
      ebb->start_ptbl_idx = ptbl_idx;
      ebb->end_ptbl_idx = ptbl_idx;
      ebb->start_reloc_idx = i;
      ebb->end_reloc_idx = i;

      if (!extend_ebb_bounds (ebb)
	  || !compute_ebb_proposed_actions (&ebb_table)
	  || !compute_ebb_actions (&ebb_table)
	  || !check_section_ebb_pcrels_fit (abfd, sec, contents,
					    internal_relocs, &ebb_table)
	  || !check_section_ebb_reduces (&ebb_table))
	{
	  /* If anything goes wrong or we get unlucky and something does
	     not fit, with our plan because of expansion between
	     critical branches, just convert to a NOP.  */

	  text_action_add (&relax_info->action_list,
			   ta_convert_longcall, sec, r_offset, 0);
	  i = ebb_table.ebb.end_reloc_idx;
	  free_ebb_constraint (&ebb_table);
	  continue;
	}

      text_action_add_proposed (&relax_info->action_list, &ebb_table, sec);

      /* Update the index so we do not go looking at the relocations
	 we have already processed.  */
      i = ebb_table.ebb.end_reloc_idx;
      free_ebb_constraint (&ebb_table);
    }

#if DEBUG
  if (relax_info->action_list.head)
    print_action_list (stderr, &relax_info->action_list);
#endif

error_return:
  release_contents (sec, contents);
  release_internal_relocs (sec, internal_relocs);
  if (prop_table)
    free (prop_table);

  return ok;
}


/* Find all of the possible actions for an extended basic block.  */

bfd_boolean
compute_ebb_proposed_actions (ebb_constraint *ebb_table)
{
  const ebb_t *ebb = &ebb_table->ebb;
  unsigned rel_idx = ebb->start_reloc_idx;
  property_table_entry *entry, *start_entry, *end_entry;

  start_entry = &ebb->ptbl[ebb->start_ptbl_idx];
  end_entry = &ebb->ptbl[ebb->end_ptbl_idx];

  for (entry = start_entry; entry <= end_entry; entry++)
    {
      bfd_vma offset, start_offset, end_offset;
      bfd_size_type insn_len;

      start_offset = entry->address - ebb->sec->vma;
      end_offset = entry->address + entry->size - ebb->sec->vma;

      if (entry == start_entry)
	start_offset = ebb->start_offset;
      if (entry == end_entry)
	end_offset = ebb->end_offset;
      offset = start_offset;

      if (offset == entry->address - ebb->sec->vma
	  && (entry->flags & XTENSA_PROP_INSN_BRANCH_TARGET) != 0)
	{
	  enum ebb_target_enum align_type = EBB_DESIRE_TGT_ALIGN;
	  BFD_ASSERT (offset != end_offset);
	  if (offset == end_offset)
	    return FALSE;

	  insn_len = insn_decode_len (ebb->contents, ebb->content_length,
				      offset);

	  /* Propose no actions for a section with an undecodable offset.  */
	  if (insn_len == 0) 
	    {
	      (*_bfd_error_handler)
		(_("%B(%A+0x%lx): could not decode instruction; possible configuration mismatch"),
		 ebb->sec->owner, ebb->sec, offset);
	      return FALSE;
	    }
	  if (check_branch_target_aligned_address (offset, insn_len))
	    align_type = EBB_REQUIRE_TGT_ALIGN;

	  ebb_propose_action (ebb_table, align_type, 0,
			      ta_none, offset, 0, TRUE);
	}

      while (offset != end_offset)
	{
	  Elf_Internal_Rela *irel;
	  xtensa_opcode opcode;

	  while (rel_idx < ebb->end_reloc_idx
		 && (ebb->relocs[rel_idx].r_offset < offset
		     || (ebb->relocs[rel_idx].r_offset == offset
			 && (ELF32_R_TYPE (ebb->relocs[rel_idx].r_info)
			     != R_XTENSA_ASM_SIMPLIFY))))
	    rel_idx++;

	  /* Check for longcall.  */
	  irel = &ebb->relocs[rel_idx];
	  if (irel->r_offset == offset
	      && ELF32_R_TYPE (irel->r_info) == R_XTENSA_ASM_SIMPLIFY)
	    {
	      bfd_size_type simplify_size;

	      simplify_size = get_asm_simplify_size (ebb->contents, 
						     ebb->content_length,
						     irel->r_offset);
	      if (simplify_size == 0)
		{
		  (*_bfd_error_handler)
		    (_("%B(%A+0x%lx): could not decode instruction for XTENSA_ASM_SIMPLIFY relocation; possible configuration mismatch"),
		     ebb->sec->owner, ebb->sec, offset);
		  return FALSE;
		}

	      ebb_propose_action (ebb_table, EBB_NO_ALIGN, 0,
				  ta_convert_longcall, offset, 0, TRUE);
	      
	      offset += simplify_size;
	      continue;
	    }

	  insn_len = insn_decode_len (ebb->contents, ebb->content_length,
				      offset);
	  /* If the instruction is undecodable, then report an error.  */
	  if (insn_len == 0)
	    {
	      (*_bfd_error_handler)
		(_("%B(%A+0x%lx): could not decode instruction; possible configuration mismatch"),
		 ebb->sec->owner, ebb->sec, offset);
	      return FALSE;
	    }
	    
	  if ((entry->flags & XTENSA_PROP_INSN_NO_DENSITY) == 0
	      && (entry->flags & XTENSA_PROP_INSN_NO_TRANSFORM) == 0
	      && narrow_instruction (ebb->contents, ebb->content_length,
				     offset, FALSE))
	    {
	      /* Add an instruction narrow action.  */
	      ebb_propose_action (ebb_table, EBB_NO_ALIGN, 0,
				  ta_narrow_insn, offset, 0, FALSE);
	      offset += insn_len;
	      continue;
	    }
	  if ((entry->flags & XTENSA_PROP_INSN_NO_TRANSFORM) == 0
	      && widen_instruction (ebb->contents, ebb->content_length,
				    offset, FALSE))
	    {
	      /* Add an instruction widen action.  */
	      ebb_propose_action (ebb_table, EBB_NO_ALIGN, 0,
				  ta_widen_insn, offset, 0, FALSE);
	      offset += insn_len;
	      continue;
	    }
	  opcode = insn_decode_opcode (ebb->contents, ebb->content_length,
				       offset, 0);
	  if (xtensa_opcode_is_loop (xtensa_default_isa, opcode))
	    {
	      /* Check for branch targets.  */
	      ebb_propose_action (ebb_table, EBB_REQUIRE_LOOP_ALIGN, 0,
				  ta_none, offset, 0, TRUE);
	      offset += insn_len;
	      continue;
	    }

	  offset += insn_len;
	}
    }

  if (ebb->ends_unreachable)
    {
      ebb_propose_action (ebb_table, EBB_NO_ALIGN, 0,
			  ta_fill, ebb->end_offset, 0, TRUE);
    }

  return TRUE;
}


/* After all of the information has collected about the
   transformations possible in an EBB, compute the appropriate actions
   here in compute_ebb_actions.  We still must check later to make
   sure that the actions do not break any relocations.  The algorithm
   used here is pretty greedy.  Basically, it removes as many no-ops
   as possible so that the end of the EBB has the same alignment
   characteristics as the original.  First, it uses narrowing, then
   fill space at the end of the EBB, and finally widenings.  If that
   does not work, it tries again with one fewer no-op removed.  The
   optimization will only be performed if all of the branch targets
   that were aligned before transformation are also aligned after the
   transformation.

   When the size_opt flag is set, ignore the branch target alignments,
   narrow all wide instructions, and remove all no-ops unless the end
   of the EBB prevents it.  */

bfd_boolean
compute_ebb_actions (ebb_constraint *ebb_table)
{
  unsigned i = 0;
  unsigned j;
  int removed_bytes = 0;
  ebb_t *ebb = &ebb_table->ebb;
  unsigned seg_idx_start = 0;
  unsigned seg_idx_end = 0;

  /* We perform this like the assembler relaxation algorithm: Start by
     assuming all instructions are narrow and all no-ops removed; then
     walk through....  */

  /* For each segment of this that has a solid constraint, check to
     see if there are any combinations that will keep the constraint.
     If so, use it.  */
  for (seg_idx_end = 0; seg_idx_end < ebb_table->action_count; seg_idx_end++)
    {
      bfd_boolean requires_text_end_align = FALSE;
      unsigned longcall_count = 0;
      unsigned longcall_convert_count = 0;
      unsigned narrowable_count = 0;
      unsigned narrowable_convert_count = 0;
      unsigned widenable_count = 0;
      unsigned widenable_convert_count = 0;

      proposed_action *action = NULL;
      int align = (1 << ebb_table->ebb.sec->alignment_power);

      seg_idx_start = seg_idx_end;

      for (i = seg_idx_start; i < ebb_table->action_count; i++)
	{
	  action = &ebb_table->actions[i];
	  if (action->action == ta_convert_longcall)
	    longcall_count++;
	  if (action->action == ta_narrow_insn)
	    narrowable_count++;
	  if (action->action == ta_widen_insn)
	    widenable_count++;
	  if (action->action == ta_fill)
	    break;
	  if (action->align_type == EBB_REQUIRE_LOOP_ALIGN)
	    break;
	  if (action->align_type == EBB_REQUIRE_TGT_ALIGN
	      && !elf32xtensa_size_opt)
	    break;
	}
      seg_idx_end = i;

      if (seg_idx_end == ebb_table->action_count && !ebb->ends_unreachable)
	requires_text_end_align = TRUE;

      if (elf32xtensa_size_opt && !requires_text_end_align
	  && action->align_type != EBB_REQUIRE_LOOP_ALIGN
	  && action->align_type != EBB_REQUIRE_TGT_ALIGN)
	{
	  longcall_convert_count = longcall_count;
	  narrowable_convert_count = narrowable_count;
	  widenable_convert_count = 0;
	}
      else
	{
	  /* There is a constraint.  Convert the max number of longcalls.  */
	  narrowable_convert_count = 0;
	  longcall_convert_count = 0;
	  widenable_convert_count = 0;

	  for (j = 0; j < longcall_count; j++)
	    {
	      int removed = (longcall_count - j) * 3 & (align - 1);
	      unsigned desire_narrow = (align - removed) & (align - 1);
	      unsigned desire_widen = removed;
	      if (desire_narrow <= narrowable_count)
		{
		  narrowable_convert_count = desire_narrow;
		  narrowable_convert_count +=
		    (align * ((narrowable_count - narrowable_convert_count)
			      / align));
		  longcall_convert_count = (longcall_count - j);
		  widenable_convert_count = 0;
		  break;
		}
	      if (desire_widen <= widenable_count && !elf32xtensa_size_opt)
		{
		  narrowable_convert_count = 0;
		  longcall_convert_count = longcall_count - j;
		  widenable_convert_count = desire_widen;
		  break;
		}
	    }
	}

      /* Now the number of conversions are saved.  Do them.  */
      for (i = seg_idx_start; i < seg_idx_end; i++)
	{
	  action = &ebb_table->actions[i];
	  switch (action->action)
	    {
	    case ta_convert_longcall:
	      if (longcall_convert_count != 0)
		{
		  action->action = ta_remove_longcall;
		  action->do_action = TRUE;
		  action->removed_bytes += 3;
		  longcall_convert_count--;
		}
	      break;
	    case ta_narrow_insn:
	      if (narrowable_convert_count != 0)
		{
		  action->do_action = TRUE;
		  action->removed_bytes += 1;
		  narrowable_convert_count--;
		}
	      break;
	    case ta_widen_insn:
	      if (widenable_convert_count != 0)
		{
		  action->do_action = TRUE;
		  action->removed_bytes -= 1;
		  widenable_convert_count--;
		}
	      break;
	    default:
	      break;
	    }
	}
    }

  /* Now we move on to some local opts.  Try to remove each of the
     remaining longcalls.  */

  if (ebb_table->ebb.ends_section || ebb_table->ebb.ends_unreachable)
    {
      removed_bytes = 0;
      for (i = 0; i < ebb_table->action_count; i++)
	{
	  int old_removed_bytes = removed_bytes;
	  proposed_action *action = &ebb_table->actions[i];

	  if (action->do_action && action->action == ta_convert_longcall)
	    {
	      bfd_boolean bad_alignment = FALSE;
	      removed_bytes += 3;
	      for (j = i + 1; j < ebb_table->action_count; j++)
		{
		  proposed_action *new_action = &ebb_table->actions[j];
		  bfd_vma offset = new_action->offset;
		  if (new_action->align_type == EBB_REQUIRE_TGT_ALIGN)
		    {
		      if (!check_branch_target_aligned
			  (ebb_table->ebb.contents,
			   ebb_table->ebb.content_length,
			   offset, offset - removed_bytes))
			{
			  bad_alignment = TRUE;
			  break;
			}
		    }
		  if (new_action->align_type == EBB_REQUIRE_LOOP_ALIGN)
		    {
		      if (!check_loop_aligned (ebb_table->ebb.contents,
					       ebb_table->ebb.content_length,
					       offset,
					       offset - removed_bytes))
			{
			  bad_alignment = TRUE;
			  break;
			}
		    }
		  if (new_action->action == ta_narrow_insn
		      && !new_action->do_action
		      && ebb_table->ebb.sec->alignment_power == 2)
		    {
		      /* Narrow an instruction and we are done.  */
		      new_action->do_action = TRUE;
		      new_action->removed_bytes += 1;
		      bad_alignment = FALSE;
		      break;
		    }
		  if (new_action->action == ta_widen_insn
		      && new_action->do_action
		      && ebb_table->ebb.sec->alignment_power == 2)
		    {
		      /* Narrow an instruction and we are done.  */
		      new_action->do_action = FALSE;
		      new_action->removed_bytes += 1;
		      bad_alignment = FALSE;
		      break;
		    }
		}
	      if (!bad_alignment)
		{
		  action->removed_bytes += 3;
		  action->action = ta_remove_longcall;
		  action->do_action = TRUE;
		}
	    }
	  removed_bytes = old_removed_bytes;
	  if (action->do_action)
	    removed_bytes += action->removed_bytes;
	}
    }

  removed_bytes = 0;
  for (i = 0; i < ebb_table->action_count; ++i)
    {
      proposed_action *action = &ebb_table->actions[i];
      if (action->do_action)
	removed_bytes += action->removed_bytes;
    }

  if ((removed_bytes % (1 << ebb_table->ebb.sec->alignment_power)) != 0
      && ebb->ends_unreachable)
    {
      proposed_action *action;
      int br;
      int extra_space;

      BFD_ASSERT (ebb_table->action_count != 0);
      action = &ebb_table->actions[ebb_table->action_count - 1];
      BFD_ASSERT (action->action == ta_fill);
      BFD_ASSERT (ebb->ends_unreachable->flags & XTENSA_PROP_UNREACHABLE);

      extra_space = compute_fill_extra_space (ebb->ends_unreachable);
      br = action->removed_bytes + removed_bytes + extra_space;
      br = br & ((1 << ebb->sec->alignment_power ) - 1);

      action->removed_bytes = extra_space - br;
    }
  return TRUE;
}


/* Use check_section_ebb_pcrels_fit to make sure that all of the
   relocations in a section will fit if a proposed set of actions
   are performed.  */

static bfd_boolean
check_section_ebb_pcrels_fit (bfd *abfd,
			      asection *sec,
			      bfd_byte *contents,
			      Elf_Internal_Rela *internal_relocs,
			      const ebb_constraint *constraint)
{
  unsigned i, j;
  Elf_Internal_Rela *irel;
  xtensa_relax_info *relax_info;

  relax_info = get_xtensa_relax_info (sec);

  for (i = 0; i < sec->reloc_count; i++)
    {
      r_reloc r_rel;
      bfd_vma orig_self_offset, orig_target_offset;
      bfd_vma self_offset, target_offset;
      int r_type;
      reloc_howto_type *howto;
      int self_removed_bytes, target_removed_bytes;

      irel = &internal_relocs[i];
      r_type = ELF32_R_TYPE (irel->r_info);

      howto = &elf_howto_table[r_type];
      /* We maintain the required invariant: PC-relative relocations
	 that fit before linking must fit after linking.  Thus we only
	 need to deal with relocations to the same section that are
	 PC-relative.  */
      if (ELF32_R_TYPE (irel->r_info) == R_XTENSA_ASM_SIMPLIFY
	  || !howto->pc_relative)
	continue;

      r_reloc_init (&r_rel, abfd, irel, contents,
		    bfd_get_section_limit (abfd, sec));

      if (r_reloc_get_section (&r_rel) != sec)
	continue;

      orig_self_offset = irel->r_offset;
      orig_target_offset = r_rel.target_offset;

      self_offset = orig_self_offset;
      target_offset = orig_target_offset;

      if (relax_info)
	{
	  self_offset = offset_with_removed_text (&relax_info->action_list,
						  orig_self_offset);
	  target_offset = offset_with_removed_text (&relax_info->action_list,
						    orig_target_offset);
	}

      self_removed_bytes = 0;
      target_removed_bytes = 0;

      for (j = 0; j < constraint->action_count; ++j)
	{
	  proposed_action *action = &constraint->actions[j];
	  bfd_vma offset = action->offset;
	  int removed_bytes = action->removed_bytes;
	  if (offset < orig_self_offset
	      || (offset == orig_self_offset && action->action == ta_fill
		  && action->removed_bytes < 0))
	    self_removed_bytes += removed_bytes;
	  if (offset < orig_target_offset
	      || (offset == orig_target_offset && action->action == ta_fill
		  && action->removed_bytes < 0))
	    target_removed_bytes += removed_bytes;
	}
      self_offset -= self_removed_bytes;
      target_offset -= target_removed_bytes;

      /* Try to encode it.  Get the operand and check.  */
      if (is_alt_relocation (ELF32_R_TYPE (irel->r_info)))
	{
	  /* None of the current alternate relocs are PC-relative,
	     and only PC-relative relocs matter here.  */
	}
      else
	{
	  xtensa_opcode opcode;
	  int opnum;

	  opcode = get_relocation_opcode (abfd, sec, contents, irel);
	  if (opcode == XTENSA_UNDEFINED)
	    return FALSE;

	  opnum = get_relocation_opnd (opcode, ELF32_R_TYPE (irel->r_info));
	  if (opnum == XTENSA_UNDEFINED)
	    return FALSE;

	  if (!pcrel_reloc_fits (opcode, opnum, self_offset, target_offset))
	    return FALSE;
	}
    }

  return TRUE;
}


static bfd_boolean
check_section_ebb_reduces (const ebb_constraint *constraint)
{
  int removed = 0;
  unsigned i;

  for (i = 0; i < constraint->action_count; i++)
    {
      const proposed_action *action = &constraint->actions[i];
      if (action->do_action)
	removed += action->removed_bytes;
    }
  if (removed < 0)
    return FALSE;

  return TRUE;
}


void
text_action_add_proposed (text_action_list *l,
			  const ebb_constraint *ebb_table,
			  asection *sec)
{
  unsigned i;

  for (i = 0; i < ebb_table->action_count; i++)
    {
      proposed_action *action = &ebb_table->actions[i];

      if (!action->do_action)
	continue;
      switch (action->action)
	{
	case ta_remove_insn:
	case ta_remove_longcall:
	case ta_convert_longcall:
	case ta_narrow_insn:
	case ta_widen_insn:
	case ta_fill:
	case ta_remove_literal:
	  text_action_add (l, action->action, sec, action->offset,
			   action->removed_bytes);
	  break;
	case ta_none:
	  break;
	default:
	  BFD_ASSERT (0);
	  break;
	}
    }
}


int
compute_fill_extra_space (property_table_entry *entry)
{
  int fill_extra_space;

  if (!entry)
    return 0;

  if ((entry->flags & XTENSA_PROP_UNREACHABLE) == 0)
    return 0;

  fill_extra_space = entry->size;
  if ((entry->flags & XTENSA_PROP_ALIGN) != 0)
    {
      /* Fill bytes for alignment:
	 (2**n)-1 - (addr + (2**n)-1) & (2**n -1) */
      int pow = GET_XTENSA_PROP_ALIGNMENT (entry->flags);
      int nsm = (1 << pow) - 1;
      bfd_vma addr = entry->address + entry->size;
      bfd_vma align_fill = nsm - ((addr + nsm) & nsm);
      fill_extra_space += align_fill;
    }
  return fill_extra_space;
}


/* First relaxation pass.  */

/* If the section contains relaxable literals, check each literal to
   see if it has the same value as another literal that has already
   been seen, either in the current section or a previous one.  If so,
   add an entry to the per-section list of removed literals.  The
   actual changes are deferred until the next pass.  */

static bfd_boolean 
compute_removed_literals (bfd *abfd,
			  asection *sec,
			  struct bfd_link_info *link_info,
			  value_map_hash_table *values)
{
  xtensa_relax_info *relax_info;
  bfd_byte *contents;
  Elf_Internal_Rela *internal_relocs;
  source_reloc *src_relocs, *rel;
  bfd_boolean ok = TRUE;
  property_table_entry *prop_table = NULL;
  int ptblsize;
  int i, prev_i;
  bfd_boolean last_loc_is_prev = FALSE;
  bfd_vma last_target_offset = 0;
  section_cache_t target_sec_cache;
  bfd_size_type sec_size;

  init_section_cache (&target_sec_cache);

  /* Do nothing if it is not a relaxable literal section.  */
  relax_info = get_xtensa_relax_info (sec);
  BFD_ASSERT (relax_info);
  if (!relax_info->is_relaxable_literal_section)
    return ok;

  internal_relocs = retrieve_internal_relocs (abfd, sec, 
					      link_info->keep_memory);

  sec_size = bfd_get_section_limit (abfd, sec);
  contents = retrieve_contents (abfd, sec, link_info->keep_memory);
  if (contents == NULL && sec_size != 0)
    {
      ok = FALSE;
      goto error_return;
    }

  /* Sort the source_relocs by target offset.  */
  src_relocs = relax_info->src_relocs;
  qsort (src_relocs, relax_info->src_count,
	 sizeof (source_reloc), source_reloc_compare);
  qsort (internal_relocs, sec->reloc_count, sizeof (Elf_Internal_Rela),
	 internal_reloc_compare);

  ptblsize = xtensa_read_table_entries (abfd, sec, &prop_table,
					XTENSA_PROP_SEC_NAME, FALSE);
  if (ptblsize < 0)
    {
      ok = FALSE;
      goto error_return;
    }

  prev_i = -1;
  for (i = 0; i < relax_info->src_count; i++)
    {
      Elf_Internal_Rela *irel = NULL;

      rel = &src_relocs[i];
      if (get_l32r_opcode () != rel->opcode)
	continue;
      irel = get_irel_at_offset (sec, internal_relocs,
				 rel->r_rel.target_offset);

      /* If the relocation on this is not a simple R_XTENSA_32 or
	 R_XTENSA_PLT then do not consider it.  This may happen when
	 the difference of two symbols is used in a literal.  */
      if (irel && (ELF32_R_TYPE (irel->r_info) != R_XTENSA_32
		   && ELF32_R_TYPE (irel->r_info) != R_XTENSA_PLT))
	continue;

      /* If the target_offset for this relocation is the same as the
	 previous relocation, then we've already considered whether the
	 literal can be coalesced.  Skip to the next one....  */
      if (i != 0 && prev_i != -1
	  && src_relocs[i-1].r_rel.target_offset == rel->r_rel.target_offset)
	continue;
      prev_i = i;

      if (last_loc_is_prev && 
	  last_target_offset + 4 != rel->r_rel.target_offset)
	last_loc_is_prev = FALSE;

      /* Check if the relocation was from an L32R that is being removed
	 because a CALLX was converted to a direct CALL, and check if
	 there are no other relocations to the literal.  */
      if (is_removable_literal (rel, i, src_relocs, relax_info->src_count))
	{
	  if (!remove_dead_literal (abfd, sec, link_info, internal_relocs,
				    irel, rel, prop_table, ptblsize))
	    {
	      ok = FALSE;
	      goto error_return;
	    }
	  last_target_offset = rel->r_rel.target_offset;
	  continue;
	}

      if (!identify_literal_placement (abfd, sec, contents, link_info,
				       values, 
				       &last_loc_is_prev, irel, 
				       relax_info->src_count - i, rel,
				       prop_table, ptblsize,
				       &target_sec_cache, rel->is_abs_literal))
	{
	  ok = FALSE;
	  goto error_return;
	}
      last_target_offset = rel->r_rel.target_offset;
    }

#if DEBUG
  print_removed_literals (stderr, &relax_info->removed_list);
  print_action_list (stderr, &relax_info->action_list);
#endif /* DEBUG */

error_return:
  if (prop_table) free (prop_table);
  clear_section_cache (&target_sec_cache);

  release_contents (sec, contents);
  release_internal_relocs (sec, internal_relocs);
  return ok;
}


static Elf_Internal_Rela *
get_irel_at_offset (asection *sec,
		    Elf_Internal_Rela *internal_relocs,
		    bfd_vma offset)
{
  unsigned i;
  Elf_Internal_Rela *irel;
  unsigned r_type;
  Elf_Internal_Rela key;

  if (!internal_relocs) 
    return NULL;

  key.r_offset = offset;
  irel = bsearch (&key, internal_relocs, sec->reloc_count,
		  sizeof (Elf_Internal_Rela), internal_reloc_matches);
  if (!irel)
    return NULL;

  /* bsearch does not guarantee which will be returned if there are
     multiple matches.  We need the first that is not an alignment.  */
  i = irel - internal_relocs;
  while (i > 0)
    {
      if (internal_relocs[i-1].r_offset != offset)
	break;
      i--;
    }
  for ( ; i < sec->reloc_count; i++)
    {
      irel = &internal_relocs[i];
      r_type = ELF32_R_TYPE (irel->r_info);
      if (irel->r_offset == offset && r_type != R_XTENSA_NONE)
	return irel;
    }

  return NULL;
}


bfd_boolean
is_removable_literal (const source_reloc *rel,
		      int i,
		      const source_reloc *src_relocs,
		      int src_count)
{
  const source_reloc *curr_rel;
  if (!rel->is_null)
    return FALSE;
  
  for (++i; i < src_count; ++i)
    {
      curr_rel = &src_relocs[i];
      /* If all others have the same target offset....  */
      if (curr_rel->r_rel.target_offset != rel->r_rel.target_offset)
	return TRUE;

      if (!curr_rel->is_null
	  && !xtensa_is_property_section (curr_rel->source_sec)
	  && !(curr_rel->source_sec->flags & SEC_DEBUGGING))
	return FALSE;
    }
  return TRUE;
}


bfd_boolean 
remove_dead_literal (bfd *abfd,
		     asection *sec,
		     struct bfd_link_info *link_info,
		     Elf_Internal_Rela *internal_relocs,
		     Elf_Internal_Rela *irel,
		     source_reloc *rel,
		     property_table_entry *prop_table,
		     int ptblsize)
{
  property_table_entry *entry;
  xtensa_relax_info *relax_info;

  relax_info = get_xtensa_relax_info (sec);
  if (!relax_info)
    return FALSE;

  entry = elf_xtensa_find_property_entry (prop_table, ptblsize,
					  sec->vma + rel->r_rel.target_offset);

  /* Mark the unused literal so that it will be removed.  */
  add_removed_literal (&relax_info->removed_list, &rel->r_rel, NULL);

  text_action_add (&relax_info->action_list,
		   ta_remove_literal, sec, rel->r_rel.target_offset, 4);

  /* If the section is 4-byte aligned, do not add fill.  */
  if (sec->alignment_power > 2) 
    {
      int fill_extra_space;
      bfd_vma entry_sec_offset;
      text_action *fa;
      property_table_entry *the_add_entry;
      int removed_diff;

      if (entry)
	entry_sec_offset = entry->address - sec->vma + entry->size;
      else
	entry_sec_offset = rel->r_rel.target_offset + 4;

      /* If the literal range is at the end of the section,
	 do not add fill.  */
      the_add_entry = elf_xtensa_find_property_entry (prop_table, ptblsize,
						      entry_sec_offset);
      fill_extra_space = compute_fill_extra_space (the_add_entry);

      fa = find_fill_action (&relax_info->action_list, sec, entry_sec_offset);
      removed_diff = compute_removed_action_diff (fa, sec, entry_sec_offset,
						  -4, fill_extra_space);
      if (fa)
	adjust_fill_action (fa, removed_diff);
      else
	text_action_add (&relax_info->action_list,
			 ta_fill, sec, entry_sec_offset, removed_diff);
    }

  /* Zero out the relocation on this literal location.  */
  if (irel)
    {
      if (elf_hash_table (link_info)->dynamic_sections_created)
	shrink_dynamic_reloc_sections (link_info, abfd, sec, irel);

      irel->r_info = ELF32_R_INFO (0, R_XTENSA_NONE);
      pin_internal_relocs (sec, internal_relocs);
    }

  /* Do not modify "last_loc_is_prev".  */
  return TRUE;
}


bfd_boolean 
identify_literal_placement (bfd *abfd,
			    asection *sec,
			    bfd_byte *contents,
			    struct bfd_link_info *link_info,
			    value_map_hash_table *values,
			    bfd_boolean *last_loc_is_prev_p,
			    Elf_Internal_Rela *irel,
			    int remaining_src_rels,
			    source_reloc *rel,
			    property_table_entry *prop_table,
			    int ptblsize,
			    section_cache_t *target_sec_cache,
			    bfd_boolean is_abs_literal)
{
  literal_value val;
  value_map *val_map;
  xtensa_relax_info *relax_info;
  bfd_boolean literal_placed = FALSE;
  r_reloc r_rel;
  unsigned long value;
  bfd_boolean final_static_link;
  bfd_size_type sec_size;

  relax_info = get_xtensa_relax_info (sec);
  if (!relax_info)
    return FALSE;

  sec_size = bfd_get_section_limit (abfd, sec);

  final_static_link =
    (!link_info->relocatable
     && !elf_hash_table (link_info)->dynamic_sections_created);

  /* The placement algorithm first checks to see if the literal is
     already in the value map.  If so and the value map is reachable
     from all uses, then the literal is moved to that location.  If
     not, then we identify the last location where a fresh literal was
     placed.  If the literal can be safely moved there, then we do so.
     If not, then we assume that the literal is not to move and leave
     the literal where it is, marking it as the last literal
     location.  */

  /* Find the literal value.  */
  value = 0;
  r_reloc_init (&r_rel, abfd, irel, contents, sec_size);
  if (!irel)
    {
      BFD_ASSERT (rel->r_rel.target_offset < sec_size);
      value = bfd_get_32 (abfd, contents + rel->r_rel.target_offset);
    }
  init_literal_value (&val, &r_rel, value, is_abs_literal);

  /* Check if we've seen another literal with the same value that
     is in the same output section.  */
  val_map = value_map_get_cached_value (values, &val, final_static_link);

  if (val_map
      && (r_reloc_get_section (&val_map->loc)->output_section
	  == sec->output_section)
      && relocations_reach (rel, remaining_src_rels, &val_map->loc)
      && coalesce_shared_literal (sec, rel, prop_table, ptblsize, val_map))
    {
      /* No change to last_loc_is_prev.  */
      literal_placed = TRUE;
    }

  /* For relocatable links, do not try to move literals.  To do it
     correctly might increase the number of relocations in an input
     section making the default relocatable linking fail.  */
  if (!link_info->relocatable && !literal_placed 
      && values->has_last_loc && !(*last_loc_is_prev_p))
    {
      asection *target_sec = r_reloc_get_section (&values->last_loc);
      if (target_sec && target_sec->output_section == sec->output_section)
	{
	  /* Increment the virtual offset.  */
	  r_reloc try_loc = values->last_loc;
	  try_loc.virtual_offset += 4;

	  /* There is a last loc that was in the same output section.  */
	  if (relocations_reach (rel, remaining_src_rels, &try_loc)
	      && move_shared_literal (sec, link_info, rel,
				      prop_table, ptblsize, 
				      &try_loc, &val, target_sec_cache))
	    {
	      values->last_loc.virtual_offset += 4;
	      literal_placed = TRUE;
	      if (!val_map)
		val_map = add_value_map (values, &val, &try_loc,
					 final_static_link);
	      else
		val_map->loc = try_loc;
	    }
	}
    }

  if (!literal_placed)
    {
      /* Nothing worked, leave the literal alone but update the last loc.  */
      values->has_last_loc = TRUE;
      values->last_loc = rel->r_rel;
      if (!val_map)
	val_map = add_value_map (values, &val, &rel->r_rel, final_static_link);
      else
	val_map->loc = rel->r_rel;
      *last_loc_is_prev_p = TRUE;
    }

  return TRUE;
}


/* Check if the original relocations (presumably on L32R instructions)
   identified by reloc[0..N] can be changed to reference the literal
   identified by r_rel.  If r_rel is out of range for any of the
   original relocations, then we don't want to coalesce the original
   literal with the one at r_rel.  We only check reloc[0..N], where the
   offsets are all the same as for reloc[0] (i.e., they're all
   referencing the same literal) and where N is also bounded by the
   number of remaining entries in the "reloc" array.  The "reloc" array
   is sorted by target offset so we know all the entries for the same
   literal will be contiguous.  */

static bfd_boolean
relocations_reach (source_reloc *reloc,
		   int remaining_relocs,
		   const r_reloc *r_rel)
{
  bfd_vma from_offset, source_address, dest_address;
  asection *sec;
  int i;

  if (!r_reloc_is_defined (r_rel))
    return FALSE;

  sec = r_reloc_get_section (r_rel);
  from_offset = reloc[0].r_rel.target_offset;

  for (i = 0; i < remaining_relocs; i++)
    {
      if (reloc[i].r_rel.target_offset != from_offset)
	break;

      /* Ignore relocations that have been removed.  */
      if (reloc[i].is_null)
	continue;

      /* The original and new output section for these must be the same
         in order to coalesce.  */
      if (r_reloc_get_section (&reloc[i].r_rel)->output_section
	  != sec->output_section)
	return FALSE;

      /* A literal with no PC-relative relocations can be moved anywhere.  */
      if (reloc[i].opnd != -1)
	{
	  /* Otherwise, check to see that it fits.  */
	  source_address = (reloc[i].source_sec->output_section->vma
			    + reloc[i].source_sec->output_offset
			    + reloc[i].r_rel.rela.r_offset);
	  dest_address = (sec->output_section->vma
			  + sec->output_offset
			  + r_rel->target_offset);

	  if (!pcrel_reloc_fits (reloc[i].opcode, reloc[i].opnd,
				 source_address, dest_address))
	    return FALSE;
	}
    }

  return TRUE;
}


/* Move a literal to another literal location because it is
   the same as the other literal value.  */

static bfd_boolean 
coalesce_shared_literal (asection *sec,
			 source_reloc *rel,
			 property_table_entry *prop_table,
			 int ptblsize,
			 value_map *val_map)
{
  property_table_entry *entry;
  text_action *fa;
  property_table_entry *the_add_entry;
  int removed_diff;
  xtensa_relax_info *relax_info;

  relax_info = get_xtensa_relax_info (sec);
  if (!relax_info)
    return FALSE;

  entry = elf_xtensa_find_property_entry
    (prop_table, ptblsize, sec->vma + rel->r_rel.target_offset);
  if (entry && (entry->flags & XTENSA_PROP_INSN_NO_TRANSFORM))
    return TRUE;

  /* Mark that the literal will be coalesced.  */
  add_removed_literal (&relax_info->removed_list, &rel->r_rel, &val_map->loc);

  text_action_add (&relax_info->action_list,
		   ta_remove_literal, sec, rel->r_rel.target_offset, 4);

  /* If the section is 4-byte aligned, do not add fill.  */
  if (sec->alignment_power > 2) 
    {
      int fill_extra_space;
      bfd_vma entry_sec_offset;

      if (entry)
	entry_sec_offset = entry->address - sec->vma + entry->size;
      else
	entry_sec_offset = rel->r_rel.target_offset + 4;

      /* If the literal range is at the end of the section,
	 do not add fill.  */
      fill_extra_space = 0;
      the_add_entry = elf_xtensa_find_property_entry (prop_table, ptblsize,
						      entry_sec_offset);
      if (the_add_entry && (the_add_entry->flags & XTENSA_PROP_UNREACHABLE))
	fill_extra_space = the_add_entry->size;

      fa = find_fill_action (&relax_info->action_list, sec, entry_sec_offset);
      removed_diff = compute_removed_action_diff (fa, sec, entry_sec_offset,
						  -4, fill_extra_space);
      if (fa)
	adjust_fill_action (fa, removed_diff);
      else
	text_action_add (&relax_info->action_list,
			 ta_fill, sec, entry_sec_offset, removed_diff);
    }

  return TRUE;
}


/* Move a literal to another location.  This may actually increase the
   total amount of space used because of alignments so we need to do
   this carefully.  Also, it may make a branch go out of range.  */

static bfd_boolean 
move_shared_literal (asection *sec,
		     struct bfd_link_info *link_info,
		     source_reloc *rel,
		     property_table_entry *prop_table,
		     int ptblsize,
		     const r_reloc *target_loc,
		     const literal_value *lit_value,
		     section_cache_t *target_sec_cache)
{
  property_table_entry *the_add_entry, *src_entry, *target_entry = NULL;
  text_action *fa, *target_fa;
  int removed_diff;
  xtensa_relax_info *relax_info, *target_relax_info;
  asection *target_sec;
  ebb_t *ebb;
  ebb_constraint ebb_table;
  bfd_boolean relocs_fit;

  /* If this routine always returns FALSE, the literals that cannot be
     coalesced will not be moved.  */
  if (elf32xtensa_no_literal_movement)
    return FALSE;

  relax_info = get_xtensa_relax_info (sec);
  if (!relax_info)
    return FALSE;

  target_sec = r_reloc_get_section (target_loc);
  target_relax_info = get_xtensa_relax_info (target_sec);

  /* Literals to undefined sections may not be moved because they
     must report an error.  */
  if (bfd_is_und_section (target_sec))
    return FALSE;

  src_entry = elf_xtensa_find_property_entry
    (prop_table, ptblsize, sec->vma + rel->r_rel.target_offset);

  if (!section_cache_section (target_sec_cache, target_sec, link_info))
    return FALSE;

  target_entry = elf_xtensa_find_property_entry
    (target_sec_cache->ptbl, target_sec_cache->pte_count, 
     target_sec->vma + target_loc->target_offset);

  if (!target_entry)
    return FALSE;

  /* Make sure that we have not broken any branches.  */
  relocs_fit = FALSE;

  init_ebb_constraint (&ebb_table);
  ebb = &ebb_table.ebb;
  init_ebb (ebb, target_sec_cache->sec, target_sec_cache->contents, 
	    target_sec_cache->content_length,
	    target_sec_cache->ptbl, target_sec_cache->pte_count,
	    target_sec_cache->relocs, target_sec_cache->reloc_count);

  /* Propose to add 4 bytes + worst-case alignment size increase to
     destination.  */
  ebb_propose_action (&ebb_table, EBB_NO_ALIGN, 0,
		      ta_fill, target_loc->target_offset,
		      -4 - (1 << target_sec->alignment_power), TRUE);

  /* Check all of the PC-relative relocations to make sure they still fit.  */
  relocs_fit = check_section_ebb_pcrels_fit (target_sec->owner, target_sec, 
					     target_sec_cache->contents,
					     target_sec_cache->relocs,
					     &ebb_table);

  if (!relocs_fit) 
    return FALSE;

  text_action_add_literal (&target_relax_info->action_list,
			   ta_add_literal, target_loc, lit_value, -4);

  if (target_sec->alignment_power > 2 && target_entry != src_entry) 
    {
      /* May need to add or remove some fill to maintain alignment.  */
      int fill_extra_space;
      bfd_vma entry_sec_offset;

      entry_sec_offset = 
	target_entry->address - target_sec->vma + target_entry->size;

      /* If the literal range is at the end of the section,
	 do not add fill.  */
      fill_extra_space = 0;
      the_add_entry =
	elf_xtensa_find_property_entry (target_sec_cache->ptbl,
					target_sec_cache->pte_count,
					entry_sec_offset);
      if (the_add_entry && (the_add_entry->flags & XTENSA_PROP_UNREACHABLE))
	fill_extra_space = the_add_entry->size;

      target_fa = find_fill_action (&target_relax_info->action_list,
				    target_sec, entry_sec_offset);
      removed_diff = compute_removed_action_diff (target_fa, target_sec,
						  entry_sec_offset, 4,
						  fill_extra_space);
      if (target_fa)
	adjust_fill_action (target_fa, removed_diff);
      else
	text_action_add (&target_relax_info->action_list,
			 ta_fill, target_sec, entry_sec_offset, removed_diff);
    }

  /* Mark that the literal will be moved to the new location.  */
  add_removed_literal (&relax_info->removed_list, &rel->r_rel, target_loc);

  /* Remove the literal.  */
  text_action_add (&relax_info->action_list,
		   ta_remove_literal, sec, rel->r_rel.target_offset, 4);

  /* If the section is 4-byte aligned, do not add fill.  */
  if (sec->alignment_power > 2 && target_entry != src_entry) 
    {
      int fill_extra_space;
      bfd_vma entry_sec_offset;

      if (src_entry)
	entry_sec_offset = src_entry->address - sec->vma + src_entry->size;
      else
	entry_sec_offset = rel->r_rel.target_offset+4;

      /* If the literal range is at the end of the section,
	 do not add fill.  */
      fill_extra_space = 0;
      the_add_entry = elf_xtensa_find_property_entry (prop_table, ptblsize,
						      entry_sec_offset);
      if (the_add_entry && (the_add_entry->flags & XTENSA_PROP_UNREACHABLE))
	fill_extra_space = the_add_entry->size;

      fa = find_fill_action (&relax_info->action_list, sec, entry_sec_offset);
      removed_diff = compute_removed_action_diff (fa, sec, entry_sec_offset,
						  -4, fill_extra_space);
      if (fa)
	adjust_fill_action (fa, removed_diff);
      else
	text_action_add (&relax_info->action_list,
			 ta_fill, sec, entry_sec_offset, removed_diff);
    }

  return TRUE;
}


/* Second relaxation pass.  */

/* Modify all of the relocations to point to the right spot, and if this
   is a relaxable section, delete the unwanted literals and fix the
   section size.  */

bfd_boolean
relax_section (bfd *abfd, asection *sec, struct bfd_link_info *link_info)
{
  Elf_Internal_Rela *internal_relocs;
  xtensa_relax_info *relax_info;
  bfd_byte *contents;
  bfd_boolean ok = TRUE;
  unsigned i;
  bfd_boolean rv = FALSE;
  bfd_boolean virtual_action;
  bfd_size_type sec_size;

  sec_size = bfd_get_section_limit (abfd, sec);
  relax_info = get_xtensa_relax_info (sec);
  BFD_ASSERT (relax_info);

  /* First translate any of the fixes that have been added already.  */
  translate_section_fixes (sec);

  /* Handle property sections (e.g., literal tables) specially.  */
  if (xtensa_is_property_section (sec))
    {
      BFD_ASSERT (!relax_info->is_relaxable_literal_section);
      return relax_property_section (abfd, sec, link_info);
    }

  internal_relocs = retrieve_internal_relocs (abfd, sec, 
					      link_info->keep_memory);
  contents = retrieve_contents (abfd, sec, link_info->keep_memory);
  if (contents == NULL && sec_size != 0)
    {
      ok = FALSE;
      goto error_return;
    }

  if (internal_relocs)
    {
      for (i = 0; i < sec->reloc_count; i++)
	{
	  Elf_Internal_Rela *irel;
	  xtensa_relax_info *target_relax_info;
	  bfd_vma source_offset, old_source_offset;
	  r_reloc r_rel;
	  unsigned r_type;
	  asection *target_sec;

	  /* Locally change the source address.
	     Translate the target to the new target address.
	     If it points to this section and has been removed,
	     NULLify it.
	     Write it back.  */

	  irel = &internal_relocs[i];
	  source_offset = irel->r_offset;
	  old_source_offset = source_offset;

	  r_type = ELF32_R_TYPE (irel->r_info);
	  r_reloc_init (&r_rel, abfd, irel, contents,
			bfd_get_section_limit (abfd, sec));

	  /* If this section could have changed then we may need to
	     change the relocation's offset.  */

	  if (relax_info->is_relaxable_literal_section
	      || relax_info->is_relaxable_asm_section)
	    {
	      if (r_type != R_XTENSA_NONE
		  && find_removed_literal (&relax_info->removed_list,
					   irel->r_offset))
		{
		  /* Remove this relocation.  */
		  if (elf_hash_table (link_info)->dynamic_sections_created)
		    shrink_dynamic_reloc_sections (link_info, abfd, sec, irel);
		  irel->r_info = ELF32_R_INFO (0, R_XTENSA_NONE);
		  irel->r_offset = offset_with_removed_text
		    (&relax_info->action_list, irel->r_offset);
		  pin_internal_relocs (sec, internal_relocs);
		  continue;
		}

	      if (r_type == R_XTENSA_ASM_SIMPLIFY)
		{
		  text_action *action =
		    find_insn_action (&relax_info->action_list,
				      irel->r_offset);
		  if (action && (action->action == ta_convert_longcall
				 || action->action == ta_remove_longcall))
		    {
		      bfd_reloc_status_type retval;
		      char *error_message = NULL;

		      retval = contract_asm_expansion (contents, sec_size,
						       irel, &error_message);
		      if (retval != bfd_reloc_ok)
			{
			  (*link_info->callbacks->reloc_dangerous)
			    (link_info, error_message, abfd, sec,
			     irel->r_offset);
			  goto error_return;
			}
		      /* Update the action so that the code that moves
			 the contents will do the right thing.  */
		      if (action->action == ta_remove_longcall)
			action->action = ta_remove_insn;
		      else
			action->action = ta_none;
		      /* Refresh the info in the r_rel.  */
		      r_reloc_init (&r_rel, abfd, irel, contents, sec_size);
		      r_type = ELF32_R_TYPE (irel->r_info);
		    }
		}

	      source_offset = offset_with_removed_text
		(&relax_info->action_list, irel->r_offset);
	      irel->r_offset = source_offset;
	    }

	  /* If the target section could have changed then
	     we may need to change the relocation's target offset.  */

	  target_sec = r_reloc_get_section (&r_rel);
	  target_relax_info = get_xtensa_relax_info (target_sec);

	  if (target_relax_info
	      && (target_relax_info->is_relaxable_literal_section
		  || target_relax_info->is_relaxable_asm_section))
	    {
	      r_reloc new_reloc;
	      reloc_bfd_fix *fix;
	      bfd_vma addend_displacement;

	      translate_reloc (&r_rel, &new_reloc);

	      if (r_type == R_XTENSA_DIFF8
		  || r_type == R_XTENSA_DIFF16
		  || r_type == R_XTENSA_DIFF32)
		{
		  bfd_vma diff_value = 0, new_end_offset, diff_mask = 0;

		  if (bfd_get_section_limit (abfd, sec) < old_source_offset)
		    {
		      (*link_info->callbacks->reloc_dangerous)
			(link_info, _("invalid relocation address"),
			 abfd, sec, old_source_offset);
		      goto error_return;
		    }

		  switch (r_type)
		    {
		    case R_XTENSA_DIFF8:
		      diff_value =
			bfd_get_8 (abfd, &contents[old_source_offset]);
		      break;
		    case R_XTENSA_DIFF16:
		      diff_value =
			bfd_get_16 (abfd, &contents[old_source_offset]);
		      break;
		    case R_XTENSA_DIFF32:
		      diff_value =
			bfd_get_32 (abfd, &contents[old_source_offset]);
		      break;
		    }

		  new_end_offset = offset_with_removed_text
		    (&target_relax_info->action_list,
		     r_rel.target_offset + diff_value);
		  diff_value = new_end_offset - new_reloc.target_offset;

		  switch (r_type)
		    {
		    case R_XTENSA_DIFF8:
		      diff_mask = 0xff;
		      bfd_put_8 (abfd, diff_value,
				 &contents[old_source_offset]);
		      break;
		    case R_XTENSA_DIFF16:
		      diff_mask = 0xffff;
		      bfd_put_16 (abfd, diff_value,
				  &contents[old_source_offset]);
		      break;
		    case R_XTENSA_DIFF32:
		      diff_mask = 0xffffffff;
		      bfd_put_32 (abfd, diff_value,
				  &contents[old_source_offset]);
		      break;
		    }

		  /* Check for overflow.  */
		  if ((diff_value & ~diff_mask) != 0)
		    {
		      (*link_info->callbacks->reloc_dangerous)
			(link_info, _("overflow after relaxation"),
			 abfd, sec, old_source_offset);
		      goto error_return;
		    }

		  pin_contents (sec, contents);
		}

	      /* FIXME: If the relocation still references a section in
		 the same input file, the relocation should be modified
		 directly instead of adding a "fix" record.  */

	      addend_displacement =
		new_reloc.target_offset + new_reloc.virtual_offset;

	      fix = reloc_bfd_fix_init (sec, source_offset, r_type, 0,
					r_reloc_get_section (&new_reloc),
					addend_displacement, TRUE);
	      add_fix (sec, fix);
	    }

	  pin_internal_relocs (sec, internal_relocs);
	}
    }

  if ((relax_info->is_relaxable_literal_section
       || relax_info->is_relaxable_asm_section)
      && relax_info->action_list.head)
    {
      /* Walk through the planned actions and build up a table
	 of move, copy and fill records.  Use the move, copy and
	 fill records to perform the actions once.  */

      bfd_size_type size = sec->size;
      int removed = 0;
      bfd_size_type final_size, copy_size, orig_insn_size;
      bfd_byte *scratch = NULL;
      bfd_byte *dup_contents = NULL;
      bfd_size_type orig_size = size;
      bfd_vma orig_dot = 0;
      bfd_vma orig_dot_copied = 0; /* Byte copied already from
					    orig dot in physical memory.  */
      bfd_vma orig_dot_vo = 0; /* Virtual offset from orig_dot.  */
      bfd_vma dup_dot = 0;

      text_action *action = relax_info->action_list.head;

      final_size = sec->size;
      for (action = relax_info->action_list.head; action;
	   action = action->next)
	{
	  final_size -= action->removed_bytes;
	}

      scratch = (bfd_byte *) bfd_zmalloc (final_size);
      dup_contents = (bfd_byte *) bfd_zmalloc (final_size);

      /* The dot is the current fill location.  */
#if DEBUG
      print_action_list (stderr, &relax_info->action_list);
#endif

      for (action = relax_info->action_list.head; action;
	   action = action->next)
	{
	  virtual_action = FALSE;
	  if (action->offset > orig_dot)
	    {
	      orig_dot += orig_dot_copied;
	      orig_dot_copied = 0;
	      orig_dot_vo = 0;
	      /* Out of the virtual world.  */
	    }

	  if (action->offset > orig_dot)
	    {
	      copy_size = action->offset - orig_dot;
	      memmove (&dup_contents[dup_dot], &contents[orig_dot], copy_size);
	      orig_dot += copy_size;
	      dup_dot += copy_size;
	      BFD_ASSERT (action->offset == orig_dot);
	    }
	  else if (action->offset < orig_dot)
	    {
	      if (action->action == ta_fill
		  && action->offset - action->removed_bytes == orig_dot)
		{
		  /* This is OK because the fill only effects the dup_dot.  */
		}
	      else if (action->action == ta_add_literal)
		{
		  /* TBD.  Might need to handle this.  */
		}
	    }
	  if (action->offset == orig_dot)
	    {
	      if (action->virtual_offset > orig_dot_vo)
		{
		  if (orig_dot_vo == 0)
		    {
		      /* Need to copy virtual_offset bytes.  Probably four.  */
		      copy_size = action->virtual_offset - orig_dot_vo;
		      memmove (&dup_contents[dup_dot],
			       &contents[orig_dot], copy_size);
		      orig_dot_copied = copy_size;
		      dup_dot += copy_size;
		    }
		  virtual_action = TRUE;
		} 
	      else
		BFD_ASSERT (action->virtual_offset <= orig_dot_vo);
	    }
	  switch (action->action)
	    {
	    case ta_remove_literal:
	    case ta_remove_insn:
	      BFD_ASSERT (action->removed_bytes >= 0);
	      orig_dot += action->removed_bytes;
	      break;

	    case ta_narrow_insn:
	      orig_insn_size = 3;
	      copy_size = 2;
	      memmove (scratch, &contents[orig_dot], orig_insn_size);
	      BFD_ASSERT (action->removed_bytes == 1);
	      rv = narrow_instruction (scratch, final_size, 0, TRUE);
	      BFD_ASSERT (rv);
	      memmove (&dup_contents[dup_dot], scratch, copy_size);
	      orig_dot += orig_insn_size;
	      dup_dot += copy_size;
	      break;

	    case ta_fill:
	      if (action->removed_bytes >= 0)
		orig_dot += action->removed_bytes;
	      else
		{
		  /* Already zeroed in dup_contents.  Just bump the
		     counters.  */
		  dup_dot += (-action->removed_bytes);
		}
	      break;

	    case ta_none:
	      BFD_ASSERT (action->removed_bytes == 0);
	      break;

	    case ta_convert_longcall:
	    case ta_remove_longcall:
	      /* These will be removed or converted before we get here.  */
	      BFD_ASSERT (0);
	      break;

	    case ta_widen_insn:
	      orig_insn_size = 2;
	      copy_size = 3;
	      memmove (scratch, &contents[orig_dot], orig_insn_size);
	      BFD_ASSERT (action->removed_bytes == -1);
	      rv = widen_instruction (scratch, final_size, 0, TRUE);
	      BFD_ASSERT (rv);
	      memmove (&dup_contents[dup_dot], scratch, copy_size);
	      orig_dot += orig_insn_size;
	      dup_dot += copy_size;
	      break;

	    case ta_add_literal:
	      orig_insn_size = 0;
	      copy_size = 4;
	      BFD_ASSERT (action->removed_bytes == -4);
	      /* TBD -- place the literal value here and insert
		 into the table.  */
	      memset (&dup_contents[dup_dot], 0, 4);
	      pin_internal_relocs (sec, internal_relocs);
	      pin_contents (sec, contents);

	      if (!move_literal (abfd, link_info, sec, dup_dot, dup_contents,
				 relax_info, &internal_relocs, &action->value))
		goto error_return;

	      if (virtual_action) 
		orig_dot_vo += copy_size;

	      orig_dot += orig_insn_size;
	      dup_dot += copy_size;
	      break;

	    default:
	      /* Not implemented yet.  */
	      BFD_ASSERT (0);
	      break;
	    }

	  size -= action->removed_bytes;
	  removed += action->removed_bytes;
	  BFD_ASSERT (dup_dot <= final_size);
	  BFD_ASSERT (orig_dot <= orig_size);
	}

      orig_dot += orig_dot_copied;
      orig_dot_copied = 0;

      if (orig_dot != orig_size)
	{
	  copy_size = orig_size - orig_dot;
	  BFD_ASSERT (orig_size > orig_dot);
	  BFD_ASSERT (dup_dot + copy_size == final_size);
	  memmove (&dup_contents[dup_dot], &contents[orig_dot], copy_size);
	  orig_dot += copy_size;
	  dup_dot += copy_size;
	}
      BFD_ASSERT (orig_size == orig_dot);
      BFD_ASSERT (final_size == dup_dot);

      /* Move the dup_contents back.  */
      if (final_size > orig_size)
	{
	  /* Contents need to be reallocated.  Swap the dup_contents into
	     contents.  */
	  sec->contents = dup_contents;
	  free (contents);
	  contents = dup_contents;
	  pin_contents (sec, contents);
	}
      else
	{
	  BFD_ASSERT (final_size <= orig_size);
	  memset (contents, 0, orig_size);
	  memcpy (contents, dup_contents, final_size);
	  free (dup_contents);
	}
      free (scratch);
      pin_contents (sec, contents);

      sec->size = final_size;
    }

 error_return:
  release_internal_relocs (sec, internal_relocs);
  release_contents (sec, contents);
  return ok;
}


static bfd_boolean 
translate_section_fixes (asection *sec)
{
  xtensa_relax_info *relax_info;
  reloc_bfd_fix *r;

  relax_info = get_xtensa_relax_info (sec);
  if (!relax_info)
    return TRUE;

  for (r = relax_info->fix_list; r != NULL; r = r->next)
    if (!translate_reloc_bfd_fix (r))
      return FALSE;

  return TRUE;
}


/* Translate a fix given the mapping in the relax info for the target
   section.  If it has already been translated, no work is required.  */

static bfd_boolean 
translate_reloc_bfd_fix (reloc_bfd_fix *fix)
{
  reloc_bfd_fix new_fix;
  asection *sec;
  xtensa_relax_info *relax_info;
  removed_literal *removed;
  bfd_vma new_offset, target_offset;

  if (fix->translated)
    return TRUE;

  sec = fix->target_sec;
  target_offset = fix->target_offset;

  relax_info = get_xtensa_relax_info (sec);
  if (!relax_info)
    {
      fix->translated = TRUE;
      return TRUE;
    }

  new_fix = *fix;

  /* The fix does not need to be translated if the section cannot change.  */
  if (!relax_info->is_relaxable_literal_section
      && !relax_info->is_relaxable_asm_section)
    {
      fix->translated = TRUE;
      return TRUE;
    }

  /* If the literal has been moved and this relocation was on an
     opcode, then the relocation should move to the new literal
     location.  Otherwise, the relocation should move within the
     section.  */

  removed = FALSE;
  if (is_operand_relocation (fix->src_type))
    {
      /* Check if the original relocation is against a literal being
	 removed.  */
      removed = find_removed_literal (&relax_info->removed_list,
				      target_offset);
    }

  if (removed) 
    {
      asection *new_sec;

      /* The fact that there is still a relocation to this literal indicates
	 that the literal is being coalesced, not simply removed.  */
      BFD_ASSERT (removed->to.abfd != NULL);

      /* This was moved to some other address (possibly another section).  */
      new_sec = r_reloc_get_section (&removed->to);
      if (new_sec != sec) 
	{
	  sec = new_sec;
	  relax_info = get_xtensa_relax_info (sec);
	  if (!relax_info || 
	      (!relax_info->is_relaxable_literal_section
	       && !relax_info->is_relaxable_asm_section))
	    {
	      target_offset = removed->to.target_offset;
	      new_fix.target_sec = new_sec;
	      new_fix.target_offset = target_offset;
	      new_fix.translated = TRUE;
	      *fix = new_fix;
	      return TRUE;
	    }
	}
      target_offset = removed->to.target_offset;
      new_fix.target_sec = new_sec;
    }

  /* The target address may have been moved within its section.  */
  new_offset = offset_with_removed_text (&relax_info->action_list,
					 target_offset);

  new_fix.target_offset = new_offset;
  new_fix.target_offset = new_offset;
  new_fix.translated = TRUE;
  *fix = new_fix;
  return TRUE;
}


/* Fix up a relocation to take account of removed literals.  */

static void
translate_reloc (const r_reloc *orig_rel, r_reloc *new_rel)
{
  asection *sec;
  xtensa_relax_info *relax_info;
  removed_literal *removed;
  bfd_vma new_offset, target_offset, removed_bytes;

  *new_rel = *orig_rel;

  if (!r_reloc_is_defined (orig_rel))
    return;
  sec = r_reloc_get_section (orig_rel);

  relax_info = get_xtensa_relax_info (sec);
  BFD_ASSERT (relax_info);

  if (!relax_info->is_relaxable_literal_section
      && !relax_info->is_relaxable_asm_section)
    return;

  target_offset = orig_rel->target_offset;

  removed = FALSE;
  if (is_operand_relocation (ELF32_R_TYPE (orig_rel->rela.r_info)))
    {
      /* Check if the original relocation is against a literal being
	 removed.  */
      removed = find_removed_literal (&relax_info->removed_list,
				      target_offset);
    }
  if (removed && removed->to.abfd)
    {
      asection *new_sec;

      /* The fact that there is still a relocation to this literal indicates
	 that the literal is being coalesced, not simply removed.  */
      BFD_ASSERT (removed->to.abfd != NULL);

      /* This was moved to some other address
	 (possibly in another section).  */
      *new_rel = removed->to;
      new_sec = r_reloc_get_section (new_rel);
      if (new_sec != sec)
	{
	  sec = new_sec;
	  relax_info = get_xtensa_relax_info (sec);
	  if (!relax_info
	      || (!relax_info->is_relaxable_literal_section
		  && !relax_info->is_relaxable_asm_section))
	    return;
	}
      target_offset = new_rel->target_offset;
    }

  /* ...and the target address may have been moved within its section.  */
  new_offset = offset_with_removed_text (&relax_info->action_list,
					 target_offset);

  /* Modify the offset and addend.  */
  removed_bytes = target_offset - new_offset;
  new_rel->target_offset = new_offset;
  new_rel->rela.r_addend -= removed_bytes;
}


/* For dynamic links, there may be a dynamic relocation for each
   literal.  The number of dynamic relocations must be computed in
   size_dynamic_sections, which occurs before relaxation.  When a
   literal is removed, this function checks if there is a corresponding
   dynamic relocation and shrinks the size of the appropriate dynamic
   relocation section accordingly.  At this point, the contents of the
   dynamic relocation sections have not yet been filled in, so there's
   nothing else that needs to be done.  */

static void
shrink_dynamic_reloc_sections (struct bfd_link_info *info,
			       bfd *abfd,
			       asection *input_section,
			       Elf_Internal_Rela *rel)
{
  Elf_Internal_Shdr *symtab_hdr;
  struct elf_link_hash_entry **sym_hashes;
  unsigned long r_symndx;
  int r_type;
  struct elf_link_hash_entry *h;
  bfd_boolean dynamic_symbol;

  symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
  sym_hashes = elf_sym_hashes (abfd);

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

  if (r_symndx < symtab_hdr->sh_info)
    h = NULL;
  else
    h = sym_hashes[r_symndx - symtab_hdr->sh_info];

  dynamic_symbol = xtensa_elf_dynamic_symbol_p (h, info);

  if ((r_type == R_XTENSA_32 || r_type == R_XTENSA_PLT)
      && (input_section->flags & SEC_ALLOC) != 0
      && (dynamic_symbol || info->shared))
    {
      bfd *dynobj;
      const char *srel_name;
      asection *srel;
      bfd_boolean is_plt = FALSE;

      dynobj = elf_hash_table (info)->dynobj;
      BFD_ASSERT (dynobj != NULL);

      if (dynamic_symbol && r_type == R_XTENSA_PLT)
	{
	  srel_name = ".rela.plt";
	  is_plt = TRUE;
	}
      else
	srel_name = ".rela.got";

      /* Reduce size of the .rela.* section by one reloc.  */
      srel = bfd_get_section_by_name (dynobj, srel_name);
      BFD_ASSERT (srel != NULL);
      BFD_ASSERT (srel->size >= sizeof (Elf32_External_Rela));
      srel->size -= sizeof (Elf32_External_Rela);

      if (is_plt)
	{
	  asection *splt, *sgotplt, *srelgot;
	  int reloc_index, chunk;

	  /* Find the PLT reloc index of the entry being removed.  This
	     is computed from the size of ".rela.plt".  It is needed to
	     figure out which PLT chunk to resize.  Usually "last index
	     = size - 1" since the index starts at zero, but in this
	     context, the size has just been decremented so there's no
	     need to subtract one.  */
	  reloc_index = srel->size / sizeof (Elf32_External_Rela);

	  chunk = reloc_index / PLT_ENTRIES_PER_CHUNK;
	  splt = elf_xtensa_get_plt_section (dynobj, chunk);
	  sgotplt = elf_xtensa_get_gotplt_section (dynobj, chunk);
	  BFD_ASSERT (splt != NULL && sgotplt != NULL);

	  /* Check if an entire PLT chunk has just been eliminated.  */
	  if (reloc_index % PLT_ENTRIES_PER_CHUNK == 0)
	    {
	      /* The two magic GOT entries for that chunk can go away.  */
	      srelgot = bfd_get_section_by_name (dynobj, ".rela.got");
	      BFD_ASSERT (srelgot != NULL);
	      srelgot->reloc_count -= 2;
	      srelgot->size -= 2 * sizeof (Elf32_External_Rela);
	      sgotplt->size -= 8;

	      /* There should be only one entry left (and it will be
		 removed below).  */
	      BFD_ASSERT (sgotplt->size == 4);
	      BFD_ASSERT (splt->size == PLT_ENTRY_SIZE);
	    }

	  BFD_ASSERT (sgotplt->size >= 4);
	  BFD_ASSERT (splt->size >= PLT_ENTRY_SIZE);

	  sgotplt->size -= 4;
	  splt->size -= PLT_ENTRY_SIZE;
	}
    }
}


/* Take an r_rel and move it to another section.  This usually
   requires extending the interal_relocation array and pinning it.  If
   the original r_rel is from the same BFD, we can complete this here.
   Otherwise, we add a fix record to let the final link fix the
   appropriate address.  Contents and internal relocations for the
   section must be pinned after calling this routine.  */

static bfd_boolean
move_literal (bfd *abfd,
	      struct bfd_link_info *link_info,
	      asection *sec,
	      bfd_vma offset,
	      bfd_byte *contents,
	      xtensa_relax_info *relax_info,
	      Elf_Internal_Rela **internal_relocs_p,
	      const literal_value *lit)
{
  Elf_Internal_Rela *new_relocs = NULL;
  size_t new_relocs_count = 0;
  Elf_Internal_Rela this_rela;
  const r_reloc *r_rel;

  r_rel = &lit->r_rel;
  BFD_ASSERT (elf_section_data (sec)->relocs == *internal_relocs_p);

  if (r_reloc_is_const (r_rel))
    bfd_put_32 (abfd, lit->value, contents + offset);
  else
    {
      int r_type;
      unsigned i;
      asection *target_sec;
      reloc_bfd_fix *fix;
      unsigned insert_at;

      r_type = ELF32_R_TYPE (r_rel->rela.r_info);
      target_sec = r_reloc_get_section (r_rel);

      /* This is the difficult case.  We have to create a fix up.  */
      this_rela.r_offset = offset;
      this_rela.r_info = ELF32_R_INFO (0, r_type);
      this_rela.r_addend =
	r_rel->target_offset - r_reloc_get_target_offset (r_rel);
      bfd_put_32 (abfd, lit->value, contents + offset);

      /* Currently, we cannot move relocations during a relocatable link.  */
      BFD_ASSERT (!link_info->relocatable);
      fix = reloc_bfd_fix_init (sec, offset, r_type, r_rel->abfd,
				r_reloc_get_section (r_rel),
				r_rel->target_offset + r_rel->virtual_offset,
				FALSE);
      /* We also need to mark that relocations are needed here.  */
      sec->flags |= SEC_RELOC;

      translate_reloc_bfd_fix (fix);
      /* This fix has not yet been translated.  */
      add_fix (sec, fix);

      /* Add the relocation.  If we have already allocated our own
	 space for the relocations and we have room for more, then use
	 it.  Otherwise, allocate new space and move the literals.  */
      insert_at = sec->reloc_count;
      for (i = 0; i < sec->reloc_count; ++i)
	{
	  if (this_rela.r_offset < (*internal_relocs_p)[i].r_offset)
	    {
	      insert_at = i;
	      break;
	    }
	}

      if (*internal_relocs_p != relax_info->allocated_relocs
	  || sec->reloc_count + 1 > relax_info->allocated_relocs_count)
	{
	  BFD_ASSERT (relax_info->allocated_relocs == NULL
		      || sec->reloc_count == relax_info->relocs_count);

	  if (relax_info->allocated_relocs_count == 0) 
	    new_relocs_count = (sec->reloc_count + 2) * 2;
	  else
	    new_relocs_count = (relax_info->allocated_relocs_count + 2) * 2;

	  new_relocs = (Elf_Internal_Rela *)
	    bfd_zmalloc (sizeof (Elf_Internal_Rela) * (new_relocs_count));
	  if (!new_relocs)
	    return FALSE;

	  /* We could handle this more quickly by finding the split point.  */
	  if (insert_at != 0)
	    memcpy (new_relocs, *internal_relocs_p,
		    insert_at * sizeof (Elf_Internal_Rela));

	  new_relocs[insert_at] = this_rela;

	  if (insert_at != sec->reloc_count)
	    memcpy (new_relocs + insert_at + 1,
		    (*internal_relocs_p) + insert_at,
		    (sec->reloc_count - insert_at) 
		    * sizeof (Elf_Internal_Rela));

	  if (*internal_relocs_p != relax_info->allocated_relocs)
	    {
	      /* The first time we re-allocate, we can only free the
		 old relocs if they were allocated with bfd_malloc.
		 This is not true when keep_memory is in effect.  */
	      if (!link_info->keep_memory)
		free (*internal_relocs_p);
	    }
	  else
	    free (*internal_relocs_p);
	  relax_info->allocated_relocs = new_relocs;
	  relax_info->allocated_relocs_count = new_relocs_count;
	  elf_section_data (sec)->relocs = new_relocs;
	  sec->reloc_count++;
	  relax_info->relocs_count = sec->reloc_count;
	  *internal_relocs_p = new_relocs;
	}
      else
	{
	  if (insert_at != sec->reloc_count)
	    {
	      unsigned idx;
	      for (idx = sec->reloc_count; idx > insert_at; idx--)
		(*internal_relocs_p)[idx] = (*internal_relocs_p)[idx-1];
	    }
	  (*internal_relocs_p)[insert_at] = this_rela;
	  sec->reloc_count++;
	  if (relax_info->allocated_relocs)
	    relax_info->relocs_count = sec->reloc_count;
	}
    }
  return TRUE;
}


/* This is similar to relax_section except that when a target is moved,
   we shift addresses up.  We also need to modify the size.  This
   algorithm does NOT allow for relocations into the middle of the
   property sections.  */

static bfd_boolean
relax_property_section (bfd *abfd,
			asection *sec,
			struct bfd_link_info *link_info)
{
  Elf_Internal_Rela *internal_relocs;
  bfd_byte *contents;
  unsigned i, nexti;
  bfd_boolean ok = TRUE;
  bfd_boolean is_full_prop_section;
  size_t last_zfill_target_offset = 0;
  asection *last_zfill_target_sec = NULL;
  bfd_size_type sec_size;

  sec_size = bfd_get_section_limit (abfd, sec);
  internal_relocs = retrieve_internal_relocs (abfd, sec, 
					      link_info->keep_memory);
  contents = retrieve_contents (abfd, sec, link_info->keep_memory);
  if (contents == NULL && sec_size != 0)
    {
      ok = FALSE;
      goto error_return;
    }

  is_full_prop_section =
    ((strcmp (sec->name, XTENSA_PROP_SEC_NAME) == 0)
     || (strncmp (sec->name, ".gnu.linkonce.prop.",
		  sizeof ".gnu.linkonce.prop." - 1) == 0));

  if (internal_relocs)
    {
      for (i = 0; i < sec->reloc_count; i++)
	{
	  Elf_Internal_Rela *irel;
	  xtensa_relax_info *target_relax_info;
	  unsigned r_type;
	  asection *target_sec;
	  literal_value val;
	  bfd_byte *size_p, *flags_p;

	  /* Locally change the source address.
	     Translate the target to the new target address.
	     If it points to this section and has been removed, MOVE IT.
	     Also, don't forget to modify the associated SIZE at
	     (offset + 4).  */

	  irel = &internal_relocs[i];
	  r_type = ELF32_R_TYPE (irel->r_info);
	  if (r_type == R_XTENSA_NONE)
	    continue;

	  /* Find the literal value.  */
	  r_reloc_init (&val.r_rel, abfd, irel, contents, sec_size);
	  size_p = &contents[irel->r_offset + 4];
	  flags_p = NULL;
	  if (is_full_prop_section)
	    {
	      flags_p = &contents[irel->r_offset + 8];
	      BFD_ASSERT (irel->r_offset + 12 <= sec_size);
	    }
	  else
	    BFD_ASSERT (irel->r_offset + 8 <= sec_size);

	  target_sec = r_reloc_get_section (&val.r_rel);
	  target_relax_info = get_xtensa_relax_info (target_sec);

	  if (target_relax_info
	      && (target_relax_info->is_relaxable_literal_section
		  || target_relax_info->is_relaxable_asm_section ))
	    {
	      /* Translate the relocation's destination.  */
	      bfd_vma new_offset, new_end_offset;
	      long old_size, new_size;

	      new_offset = offset_with_removed_text
		(&target_relax_info->action_list, val.r_rel.target_offset);

	      /* Assert that we are not out of bounds.  */
	      old_size = bfd_get_32 (abfd, size_p);

	      if (old_size == 0)
		{
		  /* Only the first zero-sized unreachable entry is
		     allowed to expand.  In this case the new offset
		     should be the offset before the fill and the new
		     size is the expansion size.  For other zero-sized
		     entries the resulting size should be zero with an
		     offset before or after the fill address depending
		     on whether the expanding unreachable entry
		     preceeds it.  */
		  if (last_zfill_target_sec
		      && last_zfill_target_sec == target_sec
		      && last_zfill_target_offset == val.r_rel.target_offset)
		    new_end_offset = new_offset;
		  else
		    {
		      new_end_offset = new_offset;
		      new_offset = offset_with_removed_text_before_fill
			(&target_relax_info->action_list,
			 val.r_rel.target_offset);

		      /* If it is not unreachable and we have not yet
			 seen an unreachable at this address, place it
			 before the fill address.  */
		      if (!flags_p
			  || (bfd_get_32 (abfd, flags_p)
			      & XTENSA_PROP_UNREACHABLE) == 0)
			new_end_offset = new_offset;
		      else
			{
			  last_zfill_target_sec = target_sec;
			  last_zfill_target_offset = val.r_rel.target_offset;
			}
		    }
		}
	      else
		{
		  new_end_offset = offset_with_removed_text_before_fill
		    (&target_relax_info->action_list,
		     val.r_rel.target_offset + old_size);
		}

	      new_size = new_end_offset - new_offset;

	      if (new_size != old_size)
		{
		  bfd_put_32 (abfd, new_size, size_p);
		  pin_contents (sec, contents);
		}

	      if (new_offset != val.r_rel.target_offset)
		{
		  bfd_vma diff = new_offset - val.r_rel.target_offset;
		  irel->r_addend += diff;
		  pin_internal_relocs (sec, internal_relocs);
		}
	    }
	}
    }

  /* Combine adjacent property table entries.  This is also done in
     finish_dynamic_sections() but at that point it's too late to
     reclaim the space in the output section, so we do this twice.  */

  if (internal_relocs && (!link_info->relocatable
			  || strcmp (sec->name, XTENSA_LIT_SEC_NAME) == 0))
    {
      Elf_Internal_Rela *last_irel = NULL;
      int removed_bytes = 0;
      bfd_vma offset, last_irel_offset;
      bfd_vma section_size;
      bfd_size_type entry_size;
      flagword predef_flags;

      if (is_full_prop_section)
	entry_size = 12;
      else
	entry_size = 8;

      predef_flags = xtensa_get_property_predef_flags (sec);

      /* Walk over memory and irels at the same time.
         This REQUIRES that the internal_relocs be sorted by offset.  */
      qsort (internal_relocs, sec->reloc_count, sizeof (Elf_Internal_Rela),
	     internal_reloc_compare);
      nexti = 0; /* Index into internal_relocs.  */

      pin_internal_relocs (sec, internal_relocs);
      pin_contents (sec, contents);

      last_irel_offset = (bfd_vma) -1;
      section_size = sec->size;
      BFD_ASSERT (section_size % entry_size == 0);

      for (offset = 0; offset < section_size; offset += entry_size)
	{
	  Elf_Internal_Rela *irel, *next_irel;
	  bfd_vma bytes_to_remove, size, actual_offset;
	  bfd_boolean remove_this_irel;
	  flagword flags;

	  irel = NULL;
	  next_irel = NULL;

	  /* Find the next two relocations (if there are that many left),
	     skipping over any R_XTENSA_NONE relocs.  On entry, "nexti" is
	     the starting reloc index.  After these two loops, "i"
	     is the index of the first non-NONE reloc past that starting
	     index, and "nexti" is the index for the next non-NONE reloc
	     after "i".  */

	  for (i = nexti; i < sec->reloc_count; i++)
	    {
	      if (ELF32_R_TYPE (internal_relocs[i].r_info) != R_XTENSA_NONE)
		{
		  irel = &internal_relocs[i];
		  break;
		}
	      internal_relocs[i].r_offset -= removed_bytes;
	    }

	  for (nexti = i + 1; nexti < sec->reloc_count; nexti++)
	    {
	      if (ELF32_R_TYPE (internal_relocs[nexti].r_info)
		  != R_XTENSA_NONE)
		{
		  next_irel = &internal_relocs[nexti];
		  break;
		}
	      internal_relocs[nexti].r_offset -= removed_bytes;
	    }

	  remove_this_irel = FALSE;
	  bytes_to_remove = 0;
	  actual_offset = offset - removed_bytes;
	  size = bfd_get_32 (abfd, &contents[actual_offset + 4]);

	  if (is_full_prop_section) 
	    flags = bfd_get_32 (abfd, &contents[actual_offset + 8]);
	  else
	    flags = predef_flags;

	  /* Check that the irels are sorted by offset,
	     with only one per address.  */
	  BFD_ASSERT (!irel || (int) irel->r_offset > (int) last_irel_offset); 
	  BFD_ASSERT (!next_irel || next_irel->r_offset > irel->r_offset);

	  /* Make sure there aren't relocs on the size or flag fields.  */
	  if ((irel && irel->r_offset == offset + 4)
	      || (is_full_prop_section 
		  && irel && irel->r_offset == offset + 8))
	    {
	      irel->r_offset -= removed_bytes;
	      last_irel_offset = irel->r_offset;
	    }
	  else if (next_irel && (next_irel->r_offset == offset + 4
				 || (is_full_prop_section 
				     && next_irel->r_offset == offset + 8)))
	    {
	      nexti += 1;
	      irel->r_offset -= removed_bytes;
	      next_irel->r_offset -= removed_bytes;
	      last_irel_offset = next_irel->r_offset;
	    }
	  else if (size == 0 && (flags & XTENSA_PROP_ALIGN) == 0
		   && (flags & XTENSA_PROP_UNREACHABLE) == 0)
	    {
	      /* Always remove entries with zero size and no alignment.  */
	      bytes_to_remove = entry_size;
	      if (irel && irel->r_offset == offset)
		{
		  remove_this_irel = TRUE;

		  irel->r_offset -= removed_bytes;
		  last_irel_offset = irel->r_offset;
		}
	    }
	  else if (irel && irel->r_offset == offset)
	    {
	      if (ELF32_R_TYPE (irel->r_info) == R_XTENSA_32)
		{
		  if (last_irel)
		    {
		      flagword old_flags;
		      bfd_vma old_size =
			bfd_get_32 (abfd, &contents[last_irel->r_offset + 4]);
		      bfd_vma old_address =
			(last_irel->r_addend
			 + bfd_get_32 (abfd, &contents[last_irel->r_offset]));
		      bfd_vma new_address =
			(irel->r_addend
			 + bfd_get_32 (abfd, &contents[actual_offset]));
		      if (is_full_prop_section) 
			old_flags = bfd_get_32
			  (abfd, &contents[last_irel->r_offset + 8]);
		      else
			old_flags = predef_flags;

		      if ((ELF32_R_SYM (irel->r_info)
			   == ELF32_R_SYM (last_irel->r_info))
			  && old_address + old_size == new_address
			  && old_flags == flags
			  && (old_flags & XTENSA_PROP_INSN_BRANCH_TARGET) == 0
			  && (old_flags & XTENSA_PROP_INSN_LOOP_TARGET) == 0)
			{
			  /* Fix the old size.  */
			  bfd_put_32 (abfd, old_size + size,
				      &contents[last_irel->r_offset + 4]);
			  bytes_to_remove = entry_size;
			  remove_this_irel = TRUE;
			}
		      else
			last_irel = irel;
		    }
		  else
		    last_irel = irel;
		}

	      irel->r_offset -= removed_bytes;
	      last_irel_offset = irel->r_offset;
	    }

	  if (remove_this_irel)
	    {
	      irel->r_info = ELF32_R_INFO (0, R_XTENSA_NONE);
	      irel->r_offset -= bytes_to_remove;
	    }

	  if (bytes_to_remove != 0)
	    {
	      removed_bytes += bytes_to_remove;
	      if (offset + bytes_to_remove < section_size)
		memmove (&contents[actual_offset],
			 &contents[actual_offset + bytes_to_remove],
			 section_size - offset - bytes_to_remove);
	    }
	}

      if (removed_bytes)
	{
	  /* Clear the removed bytes.  */
	  memset (&contents[section_size - removed_bytes], 0, removed_bytes);

	  sec->size = section_size - removed_bytes;

	  if (xtensa_is_littable_section (sec))
	    {
	      bfd *dynobj = elf_hash_table (link_info)->dynobj;
	      if (dynobj)
		{
		  asection *sgotloc =
		    bfd_get_section_by_name (dynobj, ".got.loc");
		  if (sgotloc)
		    sgotloc->size -= removed_bytes;
		}
	    }
	}
    }

 error_return:
  release_internal_relocs (sec, internal_relocs);
  release_contents (sec, contents);
  return ok;
}


/* Third relaxation pass.  */

/* Change symbol values to account for removed literals.  */

bfd_boolean
relax_section_symbols (bfd *abfd, asection *sec)
{
  xtensa_relax_info *relax_info;
  unsigned int sec_shndx;
  Elf_Internal_Shdr *symtab_hdr;
  Elf_Internal_Sym *isymbuf;
  unsigned i, num_syms, num_locals;

  relax_info = get_xtensa_relax_info (sec);
  BFD_ASSERT (relax_info);

  if (!relax_info->is_relaxable_literal_section
      && !relax_info->is_relaxable_asm_section)
    return TRUE;

  sec_shndx = _bfd_elf_section_from_bfd_section (abfd, sec);

  symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
  isymbuf = retrieve_local_syms (abfd);

  num_syms = symtab_hdr->sh_size / sizeof (Elf32_External_Sym);
  num_locals = symtab_hdr->sh_info;

  /* Adjust the local symbols defined in this section.  */
  for (i = 0; i < num_locals; i++)
    {
      Elf_Internal_Sym *isym = &isymbuf[i];

      if (isym->st_shndx == sec_shndx)
	{
	  bfd_vma new_address = offset_with_removed_text
	    (&relax_info->action_list, isym->st_value);
	  bfd_vma new_size = isym->st_size;

	  if (ELF32_ST_TYPE (isym->st_info) == STT_FUNC)
	    {
	      bfd_vma new_end = offset_with_removed_text
		(&relax_info->action_list, isym->st_value + isym->st_size);
	      new_size = new_end - new_address;
	    }

	  isym->st_value = new_address;
	  isym->st_size = new_size;
	}
    }

  /* Now adjust the global symbols defined in this section.  */
  for (i = 0; i < (num_syms - num_locals); i++)
    {
      struct elf_link_hash_entry *sym_hash;

      sym_hash = elf_sym_hashes (abfd)[i];

      if (sym_hash->root.type == bfd_link_hash_warning)
	sym_hash = (struct elf_link_hash_entry *) sym_hash->root.u.i.link;

      if ((sym_hash->root.type == bfd_link_hash_defined
	   || sym_hash->root.type == bfd_link_hash_defweak)
	  && sym_hash->root.u.def.section == sec)
	{
	  bfd_vma new_address = offset_with_removed_text
	    (&relax_info->action_list, sym_hash->root.u.def.value);
	  bfd_vma new_size = sym_hash->size;

	  if (sym_hash->type == STT_FUNC)
	    {
	      bfd_vma new_end = offset_with_removed_text
		(&relax_info->action_list,
		 sym_hash->root.u.def.value + sym_hash->size);
	      new_size = new_end - new_address;
	    }

	  sym_hash->root.u.def.value = new_address;
	  sym_hash->size = new_size;
	}
    }

  return TRUE;
}


/* "Fix" handling functions, called while performing relocations.  */

static bfd_boolean
do_fix_for_relocatable_link (Elf_Internal_Rela *rel,
			     bfd *input_bfd,
			     asection *input_section,
			     bfd_byte *contents)
{
  r_reloc r_rel;
  asection *sec, *old_sec;
  bfd_vma old_offset;
  int r_type = ELF32_R_TYPE (rel->r_info);
  reloc_bfd_fix *fix;

  if (r_type == R_XTENSA_NONE)
    return TRUE;

  fix = get_bfd_fix (input_section, rel->r_offset, r_type);
  if (!fix)
    return TRUE;

  r_reloc_init (&r_rel, input_bfd, rel, contents,
		bfd_get_section_limit (input_bfd, input_section));
  old_sec = r_reloc_get_section (&r_rel);
  old_offset = r_rel.target_offset;

  if (!old_sec || !r_reloc_is_defined (&r_rel))
    {
      if (r_type != R_XTENSA_ASM_EXPAND)
	{
	  (*_bfd_error_handler)
	    (_("%B(%A+0x%lx): unexpected fix for %s relocation"),
	     input_bfd, input_section, rel->r_offset,
	     elf_howto_table[r_type].name);
	  return FALSE;
	}
      /* Leave it be.  Resolution will happen in a later stage.  */
    }
  else
    {
      sec = fix->target_sec;
      rel->r_addend += ((sec->output_offset + fix->target_offset)
			- (old_sec->output_offset + old_offset));
    }
  return TRUE;
}


static void
do_fix_for_final_link (Elf_Internal_Rela *rel,
		       bfd *input_bfd,
		       asection *input_section,
		       bfd_byte *contents,
		       bfd_vma *relocationp)
{
  asection *sec;
  int r_type = ELF32_R_TYPE (rel->r_info);
  reloc_bfd_fix *fix;
  bfd_vma fixup_diff;

  if (r_type == R_XTENSA_NONE)
    return;

  fix = get_bfd_fix (input_section, rel->r_offset, r_type);
  if (!fix)
    return;

  sec = fix->target_sec;

  fixup_diff = rel->r_addend;
  if (elf_howto_table[fix->src_type].partial_inplace)
    {
      bfd_vma inplace_val;
      BFD_ASSERT (fix->src_offset
		  < bfd_get_section_limit (input_bfd, input_section));
      inplace_val = bfd_get_32 (input_bfd, &contents[fix->src_offset]);
      fixup_diff += inplace_val;
    }

  *relocationp = (sec->output_section->vma
		  + sec->output_offset
		  + fix->target_offset - fixup_diff);
}


/* Miscellaneous utility functions....  */

static asection *
elf_xtensa_get_plt_section (bfd *dynobj, int chunk)
{
  char plt_name[10];

  if (chunk == 0)
    return bfd_get_section_by_name (dynobj, ".plt");

  sprintf (plt_name, ".plt.%u", chunk);
  return bfd_get_section_by_name (dynobj, plt_name);
}


static asection *
elf_xtensa_get_gotplt_section (bfd *dynobj, int chunk)
{
  char got_name[14];

  if (chunk == 0)
    return bfd_get_section_by_name (dynobj, ".got.plt");

  sprintf (got_name, ".got.plt.%u", chunk);
  return bfd_get_section_by_name (dynobj, got_name);
}


/* Get the input section for a given symbol index.
   If the symbol is:
   . a section symbol, return the section;
   . a common symbol, return the common section;
   . an undefined symbol, return the undefined section;
   . an indirect symbol, follow the links;
   . an absolute value, return the absolute section.  */

static asection *
get_elf_r_symndx_section (bfd *abfd, unsigned long r_symndx)
{
  Elf_Internal_Shdr *symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
  asection *target_sec = NULL;
  if (r_symndx < symtab_hdr->sh_info)
    {
      Elf_Internal_Sym *isymbuf;
      unsigned int section_index;

      isymbuf = retrieve_local_syms (abfd);
      section_index = isymbuf[r_symndx].st_shndx;

      if (section_index == SHN_UNDEF)
	target_sec = bfd_und_section_ptr;
      else if (section_index > 0 && section_index < SHN_LORESERVE)
	target_sec = bfd_section_from_elf_index (abfd, section_index);
      else if (section_index == SHN_ABS)
	target_sec = bfd_abs_section_ptr;
      else if (section_index == SHN_COMMON)
	target_sec = bfd_com_section_ptr;
      else
	/* Who knows?  */
	target_sec = NULL;
    }
  else
    {
      unsigned long indx = r_symndx - symtab_hdr->sh_info;
      struct elf_link_hash_entry *h = elf_sym_hashes (abfd)[indx];

      while (h->root.type == bfd_link_hash_indirect
             || h->root.type == bfd_link_hash_warning)
        h = (struct elf_link_hash_entry *) h->root.u.i.link;

      switch (h->root.type)
	{
	case bfd_link_hash_defined:
	case  bfd_link_hash_defweak:
	  target_sec = h->root.u.def.section;
	  break;
	case bfd_link_hash_common:
	  target_sec = bfd_com_section_ptr;
	  break;
	case bfd_link_hash_undefined:
	case bfd_link_hash_undefweak:
	  target_sec = bfd_und_section_ptr;
	  break;
	default: /* New indirect warning.  */
	  target_sec = bfd_und_section_ptr;
	  break;
	}
    }
  return target_sec;
}


static struct elf_link_hash_entry *
get_elf_r_symndx_hash_entry (bfd *abfd, unsigned long r_symndx)
{
  unsigned long indx;
  struct elf_link_hash_entry *h;
  Elf_Internal_Shdr *symtab_hdr = &elf_tdata (abfd)->symtab_hdr;

  if (r_symndx < symtab_hdr->sh_info)
    return NULL;

  indx = r_symndx - symtab_hdr->sh_info;
  h = elf_sym_hashes (abfd)[indx];
  while (h->root.type == bfd_link_hash_indirect
	 || h->root.type == bfd_link_hash_warning)
    h = (struct elf_link_hash_entry *) h->root.u.i.link;
  return h;
}


/* Get the section-relative offset for a symbol number.  */

static bfd_vma
get_elf_r_symndx_offset (bfd *abfd, unsigned long r_symndx)
{
  Elf_Internal_Shdr *symtab_hdr = &elf_tdata (abfd)->symtab_hdr;
  bfd_vma offset = 0;

  if (r_symndx < symtab_hdr->sh_info)
    {
      Elf_Internal_Sym *isymbuf;
      isymbuf = retrieve_local_syms (abfd);
      offset = isymbuf[r_symndx].st_value;
    }
  else
    {
      unsigned long indx = r_symndx - symtab_hdr->sh_info;
      struct elf_link_hash_entry *h =
	elf_sym_hashes (abfd)[indx];

      while (h->root.type == bfd_link_hash_indirect
             || h->root.type == bfd_link_hash_warning)
	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)
	offset = h->root.u.def.value;
    }
  return offset;
}


static bfd_boolean
is_reloc_sym_weak (bfd *abfd, Elf_Internal_Rela *rel)
{
  unsigned long r_symndx = ELF32_R_SYM (rel->r_info);
  struct elf_link_hash_entry *h;

  h = get_elf_r_symndx_hash_entry (abfd, r_symndx);
  if (h && h->root.type == bfd_link_hash_defweak)
    return TRUE;
  return FALSE;
}


static bfd_boolean
pcrel_reloc_fits (xtensa_opcode opc,
		  int opnd,
		  bfd_vma self_address,
		  bfd_vma dest_address)
{
  xtensa_isa isa = xtensa_default_isa;
  uint32 valp = dest_address;
  if (xtensa_operand_do_reloc (isa, opc, opnd, &valp, self_address)
      || xtensa_operand_encode (isa, opc, opnd, &valp))
    return FALSE;
  return TRUE;
}


static int linkonce_len = sizeof (".gnu.linkonce.") - 1;
static int insn_sec_len = sizeof (XTENSA_INSN_SEC_NAME) - 1;
static int lit_sec_len = sizeof (XTENSA_LIT_SEC_NAME) - 1;
static int prop_sec_len = sizeof (XTENSA_PROP_SEC_NAME) - 1;


static bfd_boolean 
xtensa_is_property_section (asection *sec)
{
  if (strncmp (XTENSA_INSN_SEC_NAME, sec->name, insn_sec_len) == 0
      || strncmp (XTENSA_LIT_SEC_NAME, sec->name, lit_sec_len) == 0
      || strncmp (XTENSA_PROP_SEC_NAME, sec->name, prop_sec_len) == 0)
    return TRUE;

  if (strncmp (".gnu.linkonce.", sec->name, linkonce_len) == 0
      && (strncmp (&sec->name[linkonce_len], "x.", 2) == 0
	  || strncmp (&sec->name[linkonce_len], "p.", 2) == 0
	  || strncmp (&sec->name[linkonce_len], "prop.", 5) == 0))
    return TRUE;

  return FALSE;
}


static bfd_boolean 
xtensa_is_littable_section (asection *sec)
{
  if (strncmp (XTENSA_LIT_SEC_NAME, sec->name, lit_sec_len) == 0)
    return TRUE;

  if (strncmp (".gnu.linkonce.", sec->name, linkonce_len) == 0
      && sec->name[linkonce_len] == 'p'
      && sec->name[linkonce_len + 1] == '.')
    return TRUE;

  return FALSE;
}


static int
internal_reloc_compare (const void *ap, const void *bp)
{
  const Elf_Internal_Rela *a = (const Elf_Internal_Rela *) ap;
  const Elf_Internal_Rela *b = (const Elf_Internal_Rela *) bp;

  if (a->r_offset != b->r_offset)
    return (a->r_offset - b->r_offset);

  /* We don't need to sort on these criteria for correctness,
     but enforcing a more strict ordering prevents unstable qsort
     from behaving differently with different implementations.
     Without the code below we get correct but different results
     on Solaris 2.7 and 2.8.  We would like to always produce the
     same results no matter the host.  */

  if (a->r_info != b->r_info)
    return (a->r_info - b->r_info);

  return (a->r_addend - b->r_addend);
}


static int
internal_reloc_matches (const void *ap, const void *bp)
{
  const Elf_Internal_Rela *a = (const Elf_Internal_Rela *) ap;
  const Elf_Internal_Rela *b = (const Elf_Internal_Rela *) bp;

  /* Check if one entry overlaps with the other; this shouldn't happen
     except when searching for a match.  */
  return (a->r_offset - b->r_offset);
}


char *
xtensa_get_property_section_name (asection *sec, const char *base_name)
{
  if (strncmp (sec->name, ".gnu.linkonce.", linkonce_len) == 0)
    {
      char *prop_sec_name;
      const char *suffix;
      char *linkonce_kind = 0;

      if (strcmp (base_name, XTENSA_INSN_SEC_NAME) == 0) 
	linkonce_kind = "x.";
      else if (strcmp (base_name, XTENSA_LIT_SEC_NAME) == 0) 
	linkonce_kind = "p.";
      else if (strcmp (base_name, XTENSA_PROP_SEC_NAME) == 0)
	linkonce_kind = "prop.";
      else
	abort ();

      prop_sec_name = (char *) bfd_malloc (strlen (sec->name)
					   + strlen (linkonce_kind) + 1);
      memcpy (prop_sec_name, ".gnu.linkonce.", linkonce_len);
      strcpy (prop_sec_name + linkonce_len, linkonce_kind);

      suffix = sec->name + linkonce_len;
      /* For backward compatibility, replace "t." instead of inserting
         the new linkonce_kind (but not for "prop" sections).  */
      if (strncmp (suffix, "t.", 2) == 0 && linkonce_kind[1] == '.')
        suffix += 2;
      strcat (prop_sec_name + linkonce_len, suffix);

      return prop_sec_name;
    }

  return strdup (base_name);
}


flagword
xtensa_get_property_predef_flags (asection *sec)
{
  if (strcmp (sec->name, XTENSA_INSN_SEC_NAME) == 0
      || strncmp (sec->name, ".gnu.linkonce.x.",
		  sizeof ".gnu.linkonce.x." - 1) == 0)
    return (XTENSA_PROP_INSN
	    | XTENSA_PROP_INSN_NO_TRANSFORM
	    | XTENSA_PROP_INSN_NO_REORDER);

  if (xtensa_is_littable_section (sec))
    return (XTENSA_PROP_LITERAL
	    | XTENSA_PROP_INSN_NO_TRANSFORM
	    | XTENSA_PROP_INSN_NO_REORDER);

  return 0;
}


/* Other functions called directly by the linker.  */

bfd_boolean
xtensa_callback_required_dependence (bfd *abfd,
				     asection *sec,
				     struct bfd_link_info *link_info,
				     deps_callback_t callback,
				     void *closure)
{
  Elf_Internal_Rela *internal_relocs;
  bfd_byte *contents;
  unsigned i;
  bfd_boolean ok = TRUE;
  bfd_size_type sec_size;

  sec_size = bfd_get_section_limit (abfd, sec);

  /* ".plt*" sections have no explicit relocations but they contain L32R
     instructions that reference the corresponding ".got.plt*" sections.  */
  if ((sec->flags & SEC_LINKER_CREATED) != 0
      && strncmp (sec->name, ".plt", 4) == 0)
    {
      asection *sgotplt;

      /* Find the corresponding ".got.plt*" section.  */
      if (sec->name[4] == '\0')
	sgotplt = bfd_get_section_by_name (sec->owner, ".got.plt");
      else
	{
	  char got_name[14];
	  int chunk = 0;

	  BFD_ASSERT (sec->name[4] == '.');
	  chunk = strtol (&sec->name[5], NULL, 10);

	  sprintf (got_name, ".got.plt.%u", chunk);
	  sgotplt = bfd_get_section_by_name (sec->owner, got_name);
	}
      BFD_ASSERT (sgotplt);

      /* Assume worst-case offsets: L32R at the very end of the ".plt"
	 section referencing a literal at the very beginning of
	 ".got.plt".  This is very close to the real dependence, anyway.  */
      (*callback) (sec, sec_size, sgotplt, 0, closure);
    }

  internal_relocs = retrieve_internal_relocs (abfd, sec, 
					      link_info->keep_memory);
  if (internal_relocs == NULL
      || sec->reloc_count == 0)
    return ok;

  /* Cache the contents for the duration of this scan.  */
  contents = retrieve_contents (abfd, sec, link_info->keep_memory);
  if (contents == NULL && sec_size != 0)
    {
      ok = FALSE;
      goto error_return;
    }

  if (!xtensa_default_isa)
    xtensa_default_isa = xtensa_isa_init (0, 0);

  for (i = 0; i < sec->reloc_count; i++)
    {
      Elf_Internal_Rela *irel = &internal_relocs[i];
      if (is_l32r_relocation (abfd, sec, contents, irel))
	{
	  r_reloc l32r_rel;
	  asection *target_sec;
	  bfd_vma target_offset;

	  r_reloc_init (&l32r_rel, abfd, irel, contents, sec_size);
	  target_sec = NULL;
	  target_offset = 0;
	  /* L32Rs must be local to the input file.  */
	  if (r_reloc_is_defined (&l32r_rel))
	    {
	      target_sec = r_reloc_get_section (&l32r_rel);
	      target_offset = l32r_rel.target_offset;
	    }
	  (*callback) (sec, irel->r_offset, target_sec, target_offset,
		       closure);
	}
    }

 error_return:
  release_internal_relocs (sec, internal_relocs);
  release_contents (sec, contents);
  return ok;
}

/* The default literal sections should always be marked as "code" (i.e.,
   SHF_EXECINSTR).  This is particularly important for the Linux kernel
   module loader so that the literals are not placed after the text.  */
static struct bfd_elf_special_section const
  xtensa_special_sections_f[]=
{
  { ".fini.literal", 13, 0, SHT_PROGBITS, SHF_ALLOC + SHF_EXECINSTR },
  { NULL,             0, 0, 0,            0 }
};

static struct bfd_elf_special_section const
  xtensa_special_sections_i[]=
{
  { ".init.literal", 13, 0, SHT_PROGBITS, SHF_ALLOC + SHF_EXECINSTR },
  { NULL,             0, 0, 0,            0 }
};
static struct bfd_elf_special_section const
  xtensa_special_sections_l[]=
{
  { ".literal",       8, 0, SHT_PROGBITS, SHF_ALLOC + SHF_EXECINSTR },
  { NULL,             0, 0, 0,            0 }
};

static struct bfd_elf_special_section const *
  elf_xtensa_special_sections[27] =
{
  NULL,				/* 'a' */
  NULL,				/* 'b' */
  NULL,				/* 'c' */
  NULL,				/* 'd' */
  NULL,				/* 'e' */
  xtensa_special_sections_f,	/* 'f' */
  NULL,				/* 'g' */
  NULL,				/* 'h' */
  xtensa_special_sections_i,	/* 'i' */
  NULL,				/* 'j' */
  NULL,				/* 'k' */
  xtensa_special_sections_l,	/* 'l' */
  NULL,				/* 'm' */
  NULL,				/* 'n' */
  NULL,				/* 'o' */
  NULL,				/* 'p' */
  NULL,				/* 'q' */
  NULL,				/* 'r' */
  NULL,				/* 's' */
  NULL,				/* 't' */
  NULL,				/* 'u' */
  NULL,				/* 'v' */
  NULL,				/* 'w' */
  NULL,				/* 'x' */
  NULL,				/* 'y' */
  NULL,				/* 'z' */
  NULL				/* other */
};


#ifndef ELF_ARCH
#define TARGET_LITTLE_SYM		bfd_elf32_xtensa_le_vec
#define TARGET_LITTLE_NAME		"elf32-xtensa-le"
#define TARGET_BIG_SYM			bfd_elf32_xtensa_be_vec
#define TARGET_BIG_NAME			"elf32-xtensa-be"
#define ELF_ARCH			bfd_arch_xtensa

/* The new EM_XTENSA value will be recognized beginning in the Xtensa T1040
   release. However, we still have to generate files with the EM_XTENSA_OLD
   value so that pre-T1040 tools can read the files.  As soon as we stop
   caring about pre-T1040 tools, the following two values should be
   swapped. At the same time, any other code that uses EM_XTENSA_OLD
   should be changed to use EM_XTENSA.  */
#define ELF_MACHINE_CODE		EM_XTENSA_OLD
#define ELF_MACHINE_ALT1		EM_XTENSA

#if XCHAL_HAVE_MMU
#define ELF_MAXPAGESIZE			(1 << XCHAL_MMU_MIN_PTE_PAGE_SIZE)
#else /* !XCHAL_HAVE_MMU */
#define ELF_MAXPAGESIZE			1
#endif /* !XCHAL_HAVE_MMU */
#endif /* ELF_ARCH */

#define elf_backend_can_gc_sections	1
#define elf_backend_can_refcount	1
#define elf_backend_plt_readonly	1
#define elf_backend_got_header_size	4
#define elf_backend_want_dynbss		0
#define elf_backend_want_got_plt	1

#define elf_info_to_howto		     elf_xtensa_info_to_howto_rela

#define bfd_elf32_bfd_merge_private_bfd_data elf_xtensa_merge_private_bfd_data
#define bfd_elf32_new_section_hook	     elf_xtensa_new_section_hook
#define bfd_elf32_bfd_print_private_bfd_data elf_xtensa_print_private_bfd_data
#define bfd_elf32_bfd_relax_section	     elf_xtensa_relax_section
#define bfd_elf32_bfd_reloc_type_lookup	     elf_xtensa_reloc_type_lookup
#define bfd_elf32_bfd_set_private_flags	     elf_xtensa_set_private_flags

#define elf_backend_adjust_dynamic_symbol    elf_xtensa_adjust_dynamic_symbol
#define elf_backend_check_relocs	     elf_xtensa_check_relocs
#define elf_backend_create_dynamic_sections  elf_xtensa_create_dynamic_sections
#define elf_backend_discard_info	     elf_xtensa_discard_info
#define elf_backend_ignore_discarded_relocs  elf_xtensa_ignore_discarded_relocs
#define elf_backend_final_write_processing   elf_xtensa_final_write_processing
#define elf_backend_finish_dynamic_sections  elf_xtensa_finish_dynamic_sections
#define elf_backend_finish_dynamic_symbol    elf_xtensa_finish_dynamic_symbol
#define elf_backend_gc_mark_hook	     elf_xtensa_gc_mark_hook
#define elf_backend_gc_sweep_hook	     elf_xtensa_gc_sweep_hook
#define elf_backend_grok_prstatus	     elf_xtensa_grok_prstatus
#define elf_backend_grok_psinfo		     elf_xtensa_grok_psinfo
#define elf_backend_hide_symbol		     elf_xtensa_hide_symbol
#define elf_backend_modify_segment_map	     elf_xtensa_modify_segment_map
#define elf_backend_object_p		     elf_xtensa_object_p
#define elf_backend_reloc_type_class	     elf_xtensa_reloc_type_class
#define elf_backend_relocate_section	     elf_xtensa_relocate_section
#define elf_backend_size_dynamic_sections    elf_xtensa_size_dynamic_sections
#define elf_backend_special_sections	     elf_xtensa_special_sections

#include "elf32-target.h"
