/* tc-sh64.c -- Assemble code for the SuperH SH SHcompact and SHmedia.
   Copyright 2000, 2001, 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009
   Free Software Foundation.

   This file is part of GAS, the GNU Assembler.

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

   GAS 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 GAS; see the file COPYING.  If not, write to
   the Free Software Foundation, 51 Franklin Street - Fifth Floor,
   Boston, MA 02110-1301, USA.  */

/* This file defines SHmedia ISA-specific functions and includes tc-sh.c.
   The SHcompact ISA is in all useful aspects the "old" sh4 as implemented
   in tc-sh.c.  Not making this file part of tc-sh.c makes it easier to
   keep a leaner sh[1-4]-only implementation.  */

#define HAVE_SH64

#include "as.h"
#include "safe-ctype.h"
#include "opcodes/sh64-opc.h"

#ifndef OBJ_ELF
#error This file assumes object output is in the ELF format
#endif

/* Suffix used when we make "datalabel" symbol copies.  It must not
   collide with anything that can normally appear in a symbol, "faked
   symbol" or local symbol.  */
#define DATALABEL_SUFFIX " DL"

/* See shmedia_md_apply_fix and shmedia_md_pcrel_from_section for usage.  */
#define SHMEDIA_MD_PCREL_FROM_FIX(FIXP) \
 ((FIXP)->fx_size + (FIXP)->fx_where + (FIXP)->fx_frag->fr_address - 4)

/* We use this internally to see which one is PT and which is a PTA/PTB
   that should be error-checked.  We give it a better name here (but not
   one that looks official).  Adding it to reloc.c would make it look too
   much of a real reloc; it is just used temporarily as a fixup-type.  */
#define SHMEDIA_BFD_RELOC_PT BFD_RELOC_12_PCREL

typedef struct
 {
   shmedia_arg_type type;

   /* These could go into a union, but that would uglify the code.  */
   int reg;
   expressionS immediate;

   /* If IMMEDIATE was a shift-expression, like "(S >> N) & 65535", where
      N = 0, 16, 32, 48, used to extract a certain 16-bit-field to make up
      a MOVI or SHORI relocation for a symbol, then we put the
      corresponding reloc-type here and modify the "immediate" expression
      to S.  Otherwise, this is just BFD_RELOC_NONE.  */
   bfd_reloc_code_real_type reloctype;
 } shmedia_operand_info;

/* Frag containing last base instruction.  This is put in the TC field in
   a frag, so we can emit fixups for fr_opcode without needing to make
   sure that the opcode is in the same frag as any variant operand.  */
fragS *sh64_last_insn_frag = NULL;

typedef struct
 {
   shmedia_operand_info operands[3];
   unsigned long ops_val;
 } shmedia_operands_info;

enum sh64_abi_values
 { sh64_abi_unspecified, sh64_abi_32, sh64_abi_64 };

/* What ISA are we assembling code for?  */
enum sh64_isa_values sh64_isa_mode = sh64_isa_unspecified;

/* What ABI was specified, if any (implicitly or explicitly)?  */
static enum sh64_abi_values sh64_abi = sh64_abi_unspecified;

/* A note that says if we're in a sequence of insns without label
   settings, segment or ISA mode changes or emitted data.  */
static bfd_boolean seen_insn = FALSE;

/* This is set to TRUE in shmedia_md_end, so that we don't emit any
   .cranges entries when the assembler calls output functions while
   grinding along after all input is seen.  */
static bfd_boolean sh64_end_of_assembly = FALSE;

/* Controlled by the option -no-mix, this invalidates mixing SHcompact and
   SHmedia code in the same section, and also invalidates mixing data and
   SHmedia code in the same section.  No .cranges will therefore be
   emitted, unless -shcompact-const-crange is specified and there is a
   constant pool in SHcompact code.  */
static bfd_boolean sh64_mix = TRUE;

static bfd_boolean sh64_shcompact_const_crange = FALSE;

/* Controlled by the option -no-expand, this says whether or not we expand
   MOVI and PT/PTA/PTB.  When we do not expand these insns to fit an
   operand, we will emit errors for operands out of range and generate the
   basic instruction and reloc for an external symbol.  */
static bfd_boolean sh64_expand = TRUE;

/* Controlled by the option -expand-pt32, this says whether we expand
   PT/PTA/PTB of an external symbol to (only) 32 or (the full) 64 bits
   when -abi=64 is in effect.  */
static bfd_boolean sh64_pt32 = FALSE;

/* When emitting a .cranges descriptor, we want to avoid getting recursive
   calls through emit_expr.  */
static bfd_boolean emitting_crange = FALSE;

/* SHmedia mnemonics.  */
static struct hash_control *shmedia_opcode_hash_control = NULL;

static const unsigned char shmedia_big_nop_pattern[4] =
 {
   (SHMEDIA_NOP_OPC >> 24) & 255, (SHMEDIA_NOP_OPC >> 16) & 255,
   (SHMEDIA_NOP_OPC >> 8) & 255, SHMEDIA_NOP_OPC & 255
 };

static const unsigned char shmedia_little_nop_pattern[4] =
 {
   SHMEDIA_NOP_OPC & 255, (SHMEDIA_NOP_OPC >> 8) & 255,
   (SHMEDIA_NOP_OPC >> 16) & 255, (SHMEDIA_NOP_OPC >> 24) & 255
 };

static void shmedia_md_begin (void);
static int shmedia_parse_reg (char *, int *, int *, shmedia_arg_type);
static void shmedia_md_assemble (char *);
static void shmedia_md_apply_fix (fixS *, valueT *);
static int shmedia_md_estimate_size_before_relax (fragS *, segT);
static int shmedia_init_reloc (arelent *, fixS *);
static char *shmedia_get_operands (shmedia_opcode_info *, char *,
				   shmedia_operands_info *);
static void s_sh64_mode (int);
static void s_sh64_abi (int);
static void shmedia_md_convert_frag (bfd *, segT, fragS *, bfd_boolean);
static void shmedia_check_limits  (offsetT *, bfd_reloc_code_real_type,
				   fixS *);
static void sh64_set_contents_type (enum sh64_elf_cr_type);
static void shmedia_get_operand (char **, shmedia_operand_info *,
				 shmedia_arg_type);
static unsigned long shmedia_immediate_op (char *, shmedia_operand_info *,
					   int, bfd_reloc_code_real_type);
static char *shmedia_parse_exp (char *, shmedia_operand_info *);
static void shmedia_frob_file_before_adjust (void);
static void sh64_emit_crange (symbolS *, symbolS *, enum sh64_elf_cr_type);
static void sh64_flush_last_crange (bfd *, asection *, void *);
static void sh64_flag_output (void);
static void sh64_update_contents_mark (bfd_boolean);
static void sh64_vtable_entry (int);
static void sh64_vtable_inherit (int);
static char *strip_datalabels (void);
static int shmedia_build_Mytes (shmedia_opcode_info *,
				shmedia_operands_info *);
static shmedia_opcode_info *shmedia_find_cooked_opcode (char **);
static unsigned long shmedia_mask_number (unsigned long,
					  bfd_reloc_code_real_type);

#include "tc-sh.c"

void
shmedia_md_end (void)
{
  symbolS *symp;

  /* First, update the last range to include whatever data was last
     emitted.  */
  sh64_update_contents_mark (TRUE);

  /* Make sure frags generated after this point are not marked with the
     wrong ISA; make them easily spottable.  We still want to distinguish
     it from sh64_isa_unspecified when we compile for SHcompact or
     SHmedia.  */
  if (sh64_isa_mode != sh64_isa_unspecified)
    sh64_isa_mode = sh64_isa_sh5_guard;

  sh64_end_of_assembly = TRUE;

  bfd_map_over_sections (stdoutput, sh64_flush_last_crange, NULL);

  /* Iterate over segments and emit the last .cranges descriptor.  */
  for (symp = symbol_rootP; symp != NULL; symp = symp->sy_next)
    {
      symbolS *mainsym = *symbol_get_tc (symp);

      /* Is this a datalabel symbol; does it have a pointer to the main
	 symbol?  */
      if (mainsym != NULL)
	{
	  /* If the datalabel symbol is undefined, check if the main
	     symbol has changed in that respect.  */
	  if (S_GET_SEGMENT (symp) == undefined_section)
	    {
	      segT symseg;

	      symseg = S_GET_SEGMENT (mainsym);

	      /* If the symbol is now defined to something that is not
		 global and without STO_SH5_ISA32, we just equate the
		 datalabel symbol to the main symbol, and the lack of
		 STO_SH5_ISA32 will handle the datalabelness.  */
	      if (symseg != undefined_section)
		{
		  if (S_GET_OTHER (mainsym) != STO_SH5_ISA32)
		    {
		      symp->sy_value.X_op = O_symbol;
		      symp->sy_value.X_add_symbol = mainsym;
		      symp->sy_value.X_op_symbol = NULL;
		      symp->sy_value.X_add_number = 0;
		      S_SET_SEGMENT (symp, S_GET_SEGMENT (mainsym));
		      symbol_set_frag (symp, &zero_address_frag);
		      copy_symbol_attributes (symp, mainsym);
		    }
		  else
		    {
		      /* An undefined symbol has since we saw it at
			 "datalabel", been defined to a BranchTarget
			 symbol.  What we need to do here is very similar
			 to when we find the "datalabel" for a defined
			 symbol.  FIXME: Break out to common function.  */
		      symbol_set_value_expression (symp,
						   symbol_get_value_expression
						   (mainsym));
		      S_SET_SEGMENT (symp, symseg);
		      symbol_set_frag (symp, symbol_get_frag (mainsym));
		      copy_symbol_attributes (symp, mainsym);

		      /* Unset the BranchTarget mark that can be set at
			 attribute-copying.  */
		      S_SET_OTHER (symp,
				   S_GET_OTHER (symp) & ~STO_SH5_ISA32);

		      /* The GLOBAL and WEAK attributes are not copied
			 over by copy_symbol_attributes.  Do it here.  */
		      if (S_IS_WEAK (mainsym))
			S_SET_WEAK (symp);
		      else if (S_IS_EXTERNAL (mainsym))
			S_SET_EXTERNAL (symp);
		    }
		}
	      else
		{
		  /* A symbol that was defined at the time we saw
		     "datalabel" can since have been attributed with being
		     weak or global.  */
		  if (S_IS_WEAK (mainsym))
		    S_SET_WEAK (symp);
		  else if (S_IS_EXTERNAL (mainsym))
		    S_SET_EXTERNAL (symp);
		}
	    }
	}
    }

  for (symp = symbol_rootP; symp != NULL; symp = symp->sy_next)
    if (S_GET_OTHER (symp) & STO_SH5_ISA32)
      symp->sy_value.X_add_number++;
}

/* When resolving symbols, the main assembler has done us a misfavour.  It
   has removed the equation to the main symbol for a datalabel reference
   that should be equal to the main symbol, e.g. when it's a global or
   weak symbol and is a non-BranchTarget symbol anyway.  We change that
   back, so that relocs are against the main symbol, not the local "section
   + offset" value.  */

static void
shmedia_frob_file_before_adjust (void)
{
  symbolS *symp;
  for (symp = symbol_rootP; symp != NULL; symp = symp->sy_next)
    {
      symbolS *mainsym = *symbol_get_tc (symp);

      if (mainsym != NULL
	  && S_GET_OTHER (mainsym) != STO_SH5_ISA32
	  && (S_IS_EXTERNAL (mainsym) || S_IS_WEAK (mainsym)))
	{
	  symp->sy_value.X_op = O_symbol;
	  symp->sy_value.X_add_symbol = mainsym;
	  symp->sy_value.X_op_symbol = NULL;
	  symp->sy_value.X_add_number = 0;

	  /* For the "equation trick" to work, we have to set the section
	     to undefined.  */
	  S_SET_SEGMENT (symp, undefined_section);
	  symbol_set_frag (symp, &zero_address_frag);
	  copy_symbol_attributes (symp, mainsym);

	  /* Don't forget to remove the STO_SH5_ISA32 attribute after
	     copying the other attributes.  */
	  S_SET_OTHER (symp, S_GET_OTHER (symp) & ~STO_SH5_ISA32);
	}
    }
}

/* We need to mark the current location after the alignment.  This is
   copied code the caller, do_align.  We mark the frag location before and
   after as we need and arrange to skip the same code in do_align.

   An alternative to code duplication is to call the do_align recursively,
   arranging to fall through into do_align if we're already here.  That
   would require do_align as an incoming function parameter, since it's
   static in read.c.  That solution was discarded a too kludgy.  */

void
sh64_do_align (int n, const char *fill, int len, int max)
{
  /* Update region, or put a data region in front.  */
  sh64_update_contents_mark (TRUE);

  /* Only make a frag if we HAVE to...  */
  if (n != 0 && !need_pass_2)
    {
      if (fill == NULL)
	{
	  if (subseg_text_p (now_seg))
	    frag_align_code (n, max);
	  else
	    frag_align (n, 0, max);
	}
      else if (len <= 1)
	frag_align (n, *fill, max);
      else
	frag_align_pattern (n, fill, len, max);
    }

  /* Update mark for current region with current type.  */
  sh64_update_contents_mark (FALSE);
}

/* The MAX_MEM_FOR_RS_ALIGN_CODE worker.  We have to find out the ISA of
   the current segment at this position.  We can't look just at
   sh64_isa_shmedia, and we can't look at frag_now.  This is brittle:
   callers are currently frag_align_code from subsegs_finish in write.c
   (end of assembly) and frag_align_code from do_align in read.c (during
   assembly).  */

int
sh64_max_mem_for_rs_align_code (void)
{
  segment_info_type *seginfo;
  fragS *mode_start_frag;
  seginfo = seg_info (now_seg);

  /* We don't use the contents type we find at the tc_segment_info_data,
     since that does not give us absolute information about the ISA; the
     contents type can presumably be CRT_DATA and we'd be none the wiser.
     Instead we use the information stored at the frag of the symbol at
     the start of this range.  If any information is missing or NULL,
     assume SHcompact.  */
  return
    /* If the current ISA mode is SHmedia, that's the mode that we're
       going to assign to the new frag, so request enough memory for
       it, even if we switch modes afterwards, otherwise we may
       allocate too little memory and end up overflowing our buffer.  */
    (sh64_isa_mode == sh64_isa_shmedia
     || (sh64_isa_mode != sh64_isa_unspecified
	 && seginfo != NULL
	 && seginfo->tc_segment_info_data.mode_start_symbol != NULL
	 && ((mode_start_frag
	      = (symbol_get_frag
		 (seginfo->tc_segment_info_data.mode_start_symbol)))
	     != NULL)
	 && mode_start_frag->tc_frag_data.isa == sh64_isa_shmedia))
    ? (3 + 4) : (2 + 1);
}

/* Put in SHmedia NOP:s if the alignment was created when in SHmedia mode.  */

void
sh64_handle_align (fragS * frag)
{
  int bytes = frag->fr_next->fr_address - frag->fr_address - frag->fr_fix;
  char * p  = frag->fr_literal + frag->fr_fix;

  if (frag->tc_frag_data.isa == sh64_isa_shmedia
      && frag->fr_type == rs_align_code)
    {
      while (bytes & 3)
	{
	  *p++ = 0;
	  bytes--;
	  frag->fr_fix += 1;
	}

      if (target_big_endian)
	{
	  memcpy (p, shmedia_big_nop_pattern,
		  sizeof shmedia_big_nop_pattern);
	  frag->fr_var = sizeof shmedia_big_nop_pattern;
	}
      else
	{
	  memcpy (p, shmedia_little_nop_pattern,
		  sizeof shmedia_little_nop_pattern);
	  frag->fr_var = sizeof shmedia_little_nop_pattern;
	}
    }
  else
    /* Punt to SHcompact function.  */
    sh_handle_align (frag);
}

/* Set SEC_SH64_ISA32 for SHmedia sections.  */

void
shmedia_frob_section_type (asection *sec)
{
  segment_info_type *seginfo;
  seginfo = seg_info (sec);

  /* This and elf32-sh64.c:sh64_elf_fake_sections are the only places
     where we use anything else than ELF header flags to communicate the
     section as containing SHmedia or other contents.  BFD SEC_* section
     flags are running out and should not be overloaded with
     target-specific semantics.  This target is ELF only (semantics not
     defined for other formats), so we use the target-specific pointer
     field of the ELF section data.  */
  if (seginfo && sh64_abi == sh64_abi_32)
    {
      struct sh64_section_data *sec_elf_data;
      flagword sec_type = 0;

      if (seginfo->tc_segment_info_data.emitted_ranges != 0)
	sec_type = SHF_SH5_ISA32_MIXED;
      else if (seginfo->tc_segment_info_data.contents_type == CRT_SH5_ISA32)
	sec_type = SHF_SH5_ISA32;

      sec_elf_data = sh64_elf_section_data (sec)->sh64_info;
      if (sec_elf_data == NULL)
	{
	  sec_elf_data = xcalloc (1, sizeof (*sec_elf_data));
	  sh64_elf_section_data (sec)->sh64_info = sec_elf_data;
	}

      sec_elf_data->contents_flags = sec_type;
    }
}

/* This function is called by write_object_file right before the symbol
   table is written.  We subtract 1 from all symbols marked STO_SH5_ISA32,
   as their values are temporarily incremented in shmedia_md_end, before
   symbols values are used by relocs and fixups.

   To increment all symbols and then decrement here is admittedly a
   hackish solution.  The alternative is to add infrastructure and hooks
   to symbol evaluation that evaluates symbols differently internally to
   the value output into the object file, but at the moment that just
   seems too much for little benefit.  */

void
sh64_adjust_symtab (void)
{
  symbolS *symp;

  for (symp = symbol_rootP; symp; symp = symbol_next (symp))
    {
      symbolS *main_symbol = *symbol_get_tc (symp);

      if (main_symbol)
	{
	  char *sym_name = (char *) S_GET_NAME (symp);

	  /* All datalabels not used in relocs should be gone by now.

	     We change those remaining to have the name of the main
	     symbol, and we set the ELF type of the symbol of the reloc to
	     STT_DATALABEL.  */
	  sym_name[strlen (sym_name) - strlen (DATALABEL_SUFFIX)] = 0;
	  elf_symbol (symbol_get_bfdsym (symp))->internal_elf_sym.st_info
	    = STT_DATALABEL;

	  /* Also set this symbol to "undefined", so we'll have only one
	     definition.  */
	  S_SET_SEGMENT (symp, undefined_section);
	}
      else if (S_GET_OTHER (symp) & STO_SH5_ISA32)
	{
	  /* It's important to change the BFD symbol value, since it is now
	     set to the GAS symbolS value.  */
	  symp->bsym->value--;

	  /* Note that we do *not* adjust symp->sy_value.X_add_number.  If
	     you do this, the test case in sh/sh64/immexpr2.s will fail.
	     This is because *after* symbols have been output but before
	     relocs are output, fixups are inspected one more time, and
	     some leftover expressions are resolved.  To resolve to the
	     same values, those expressions must have the same GAS symbol
	     values before as after symbols have been output.  We could
	     "symp->sy_value.X_add_number++" on the STO_SH5_ISA32 symbols
	     through tc_frob_file after symbols have been output, but that
	     would be too gross.  */
	}
    }
}

/* Fill-in an allocated arelent.  */

static int
shmedia_init_reloc (arelent *rel, fixS *fixP)
{
  /* Adjust parts of *relp according to *fixp, and tell that it has been
     done, so default initializations will not happen.   */
  switch (fixP->fx_r_type)
    {
    case BFD_RELOC_64:
    case BFD_RELOC_64_PCREL:
    case BFD_RELOC_SH_IMM_LOW16:
    case BFD_RELOC_SH_IMM_MEDLOW16:
    case BFD_RELOC_SH_IMM_MEDHI16:
    case BFD_RELOC_SH_IMM_HI16:
    case BFD_RELOC_SH_IMM_LOW16_PCREL:
    case BFD_RELOC_SH_IMM_MEDLOW16_PCREL:
    case BFD_RELOC_SH_IMM_MEDHI16_PCREL:
    case BFD_RELOC_SH_IMM_HI16_PCREL:
    case BFD_RELOC_SH_IMMU5:
    case BFD_RELOC_SH_IMMU6:
    case BFD_RELOC_SH_IMMS6:
    case BFD_RELOC_SH_IMMS10:
    case BFD_RELOC_SH_IMMS10BY2:
    case BFD_RELOC_SH_IMMS10BY4:
    case BFD_RELOC_SH_IMMS10BY8:
    case BFD_RELOC_SH_IMMS16:
    case BFD_RELOC_SH_IMMU16:
    case BFD_RELOC_SH_PT_16:
    case BFD_RELOC_SH_GOT_LOW16:
    case BFD_RELOC_SH_GOT_MEDLOW16:
    case BFD_RELOC_SH_GOT_MEDHI16:
    case BFD_RELOC_SH_GOT_HI16:
    case BFD_RELOC_SH_GOT10BY4:
    case BFD_RELOC_SH_GOT10BY8:
    case BFD_RELOC_SH_GOTPLT_LOW16:
    case BFD_RELOC_SH_GOTPLT_MEDLOW16:
    case BFD_RELOC_SH_GOTPLT_MEDHI16:
    case BFD_RELOC_SH_GOTPLT_HI16:
    case BFD_RELOC_SH_GOTPLT10BY4:
    case BFD_RELOC_SH_GOTPLT10BY8:
    case BFD_RELOC_SH_GOTOFF_LOW16:
    case BFD_RELOC_SH_GOTOFF_MEDLOW16:
    case BFD_RELOC_SH_GOTOFF_MEDHI16:
    case BFD_RELOC_SH_GOTOFF_HI16:
    case BFD_RELOC_SH_GOTPC_LOW16:
    case BFD_RELOC_SH_GOTPC_MEDLOW16:
    case BFD_RELOC_SH_GOTPC_MEDHI16:
    case BFD_RELOC_SH_GOTPC_HI16:
    case BFD_RELOC_SH_PLT_LOW16:
    case BFD_RELOC_SH_PLT_MEDLOW16:
    case BFD_RELOC_SH_PLT_MEDHI16:
    case BFD_RELOC_SH_PLT_HI16:
      rel->addend = fixP->fx_addnumber + fixP->fx_offset;
      return 1;

    case BFD_RELOC_SH_IMMS6BY32:
      /* This must be resolved in assembly; we do not support it as a
	 reloc in an object file.  */
      as_bad_where (fixP->fx_file, fixP->fx_line,
		    _("This operand must be constant at assembly time"));
      break;

      /* There are valid cases where we get here for other than SHmedia
	 relocs, so don't make a BAD_CASE out of this.  */
    default:
      ;
    }

  return 0;
}

/* Hook called from md_apply_fix in tc-sh.c.  */

static void
shmedia_md_apply_fix (fixS *fixP, valueT *valp)
{
  offsetT val = *valp;
  char *buf = fixP->fx_where + fixP->fx_frag->fr_literal;
  unsigned long insn
    = target_big_endian ? bfd_getb32 (buf) : bfd_getl32 (buf);
  bfd_reloc_code_real_type orig_fx_r_type = fixP->fx_r_type;

  /* Change a 64-bit pc-relative reloc into the correct type, just like
     tc-sh.c:md_apply_fix.  */
  if (fixP->fx_pcrel)
    {
      switch (orig_fx_r_type)
	{
	case BFD_RELOC_64:
	case BFD_RELOC_SH_IMM_LOW16:
	case BFD_RELOC_SH_IMM_MEDLOW16:
	case BFD_RELOC_SH_IMM_MEDHI16:
	case BFD_RELOC_SH_IMM_HI16:
	  /* Because write.c calls MD_PCREL_FROM_SECTION twice, we need to
	     undo one of the adjustments, if the relocation is not
	     actually for a symbol within the same segment (which we
	     cannot check, because we're not called from md_apply_fix, so
	     we have to keep the reloc).  FIXME: This is a bug in
	     write.c:fixup_segment affecting most targets that change
	     ordinary relocs to pcrel relocs in md_apply_fix.  */
	  fixP->fx_offset
	    = *valp + SHMEDIA_MD_PCREL_FROM_FIX (fixP);
	  break;

	case BFD_RELOC_SH_PLT_LOW16:
	case BFD_RELOC_SH_PLT_MEDLOW16:
	case BFD_RELOC_SH_PLT_MEDHI16:
	case BFD_RELOC_SH_PLT_HI16:
	case BFD_RELOC_SH_GOTPC_LOW16:
	case BFD_RELOC_SH_GOTPC_MEDLOW16:
	case BFD_RELOC_SH_GOTPC_MEDHI16:
	case BFD_RELOC_SH_GOTPC_HI16:
	  *valp = 0;
	  return;

	default:
	  ;
	}

      /* We might need to change some relocs into the corresponding
	 PC-relative one.  */
      switch (orig_fx_r_type)
	{
	case BFD_RELOC_64:
	  fixP->fx_r_type = BFD_RELOC_64_PCREL;
	  break;

	case BFD_RELOC_SH_IMM_LOW16:
	  fixP->fx_r_type = BFD_RELOC_SH_IMM_LOW16_PCREL;
	  break;

	case BFD_RELOC_SH_IMM_MEDLOW16:
	  fixP->fx_r_type = BFD_RELOC_SH_IMM_MEDLOW16_PCREL;
	  break;

	case BFD_RELOC_SH_IMM_MEDHI16:
	  fixP->fx_r_type = BFD_RELOC_SH_IMM_MEDHI16_PCREL;
	  break;

	case BFD_RELOC_SH_IMM_HI16:
	  fixP->fx_r_type = BFD_RELOC_SH_IMM_HI16_PCREL;
	  break;

	case SHMEDIA_BFD_RELOC_PT:
	  /* This is how we see a difference between PT and PTA when not
	     expanding (in which case we handle it in
	     shmedia_md_convert_frag).  Note that we don't see a
	     difference after the reloc is emitted.  */
	  fixP->fx_r_type = BFD_RELOC_SH_PT_16;
	  break;

	case BFD_RELOC_SH_PT_16:
	  /* This tells us there was a PTA or PTB insn explicitly
	     expressed as such (not as PT).  We "or" in a 1 into the
	     lowest bit in the (unused) destination field to tell the
	     linker that it should check the right ISA type of the
	     destination and not just change a PTA to PTB (if necessary).  */
	  md_number_to_chars (buf, insn | (1 << 10), 4);
	  break;

	case BFD_RELOC_64_PCREL:
	case BFD_RELOC_SH_IMM_LOW16_PCREL:
	case BFD_RELOC_SH_IMM_MEDLOW16_PCREL:
	case BFD_RELOC_SH_IMM_MEDHI16_PCREL:
	case BFD_RELOC_SH_IMM_HI16_PCREL:
	  /* Already handled.  */
	  break;

	default:
	  /* Everything else that changes into a pc-relative relocation is
	     an error.  */
	  as_bad_where (fixP->fx_file, fixP->fx_line,
			_("Invalid operand expression"));
	  break;
	}

      return;
    }

  /* If an expression looked like it was PC-relative, but was completely
     resolvable, we end up here with the result only in *VALP, and no
     relocation will be emitted.  */
  if (fixP->fx_addsy == NULL && fixP->fx_pcrel == 0)
    {
      /* Emit error for an out-of-range value.  */
      shmedia_check_limits ((offsetT *) valp, fixP->fx_r_type, fixP);

      switch (fixP->fx_r_type)
	{
	case BFD_RELOC_SH_IMM_LOW16:
	  md_number_to_chars (buf, insn | ((val & 65535) << 10), 4);
	  break;

	case BFD_RELOC_SH_IMM_MEDLOW16:
	  md_number_to_chars (buf,
			      insn
			      | ((valueT) (val & ((valueT) 65535 << 16))
				 >> (16 - 10)), 4);
	  break;

	case BFD_RELOC_SH_IMM_MEDHI16:
	  md_number_to_chars (buf,
			      insn
			      | ((valueT) (val & ((valueT) 65535 << 32))
				 >> (32 - 10)), 4);
	  break;

	case BFD_RELOC_SH_IMM_HI16:
	  md_number_to_chars (buf,
			      insn
			      | ((valueT) (val & ((valueT) 65535 << 48))
				 >> (48 - 10)), 4);
	  break;

	case BFD_RELOC_SH_IMMS16:
	case BFD_RELOC_SH_IMMU16:
	  md_number_to_chars (buf, insn | ((val & 65535) << 10), 4);
	  break;

	case BFD_RELOC_SH_IMMS10:
	  md_number_to_chars (buf, insn | ((val & 0x3ff) << 10), 4);
	  break;

	case BFD_RELOC_SH_IMMS10BY2:
	  md_number_to_chars (buf,
			      insn | ((val & (0x3ff << 1)) << (10 - 1)), 4);
	  break;

	case BFD_RELOC_SH_IMMS10BY4:
	  md_number_to_chars (buf,
			      insn | ((val & (0x3ff << 2)) << (10 - 2)), 4);
	  break;

	case BFD_RELOC_SH_IMMS10BY8:
	  md_number_to_chars (buf,
			      insn | ((val & (0x3ff << 3)) << (10 - 3)), 4);
	  break;

	case BFD_RELOC_SH_SHMEDIA_CODE:
	  /* We just ignore and remove this one for the moment.  FIXME:
	     Use it when implementing relaxing.  */
	  break;

	case BFD_RELOC_64:
	  md_number_to_chars (buf, val, 8);
	  break;

	case SHMEDIA_BFD_RELOC_PT:
	  /* Change a PT to PTB if the operand turned out to be SHcompact.
	     The basic opcode specified with PT is equivalent to PTA.  */
	  if ((val & 1) == 0)
	    insn |= SHMEDIA_PTB_BIT;
	  /* Fall through.  */

	case BFD_RELOC_SH_PT_16:
	  if (! sh64_expand || sh_relax)
	    {
	      /* Check if the operand of a PTA or PTB was for the "wrong"
		 ISA.  A PT had an incoming fixup of SHMEDIA_BFD_RELOC_PT,
		 which we have changed to the right type above.  */
	      if (orig_fx_r_type != SHMEDIA_BFD_RELOC_PT)
		{
		  if ((insn & SHMEDIA_PTB_BIT) != 0 && (val & 1) != 0)
		    as_bad_where (fixP->fx_file, fixP->fx_line,
				  _("PTB operand is a SHmedia symbol"));
		  else if ((insn & SHMEDIA_PTB_BIT) == 0 && (val & 1) == 0)
		    as_bad_where (fixP->fx_file, fixP->fx_line,
				  _("PTA operand is a SHcompact symbol"));
		}

	      md_number_to_chars (buf,
				  insn | ((val & (0xffff << 2))
					  << (10 - 2)),
				  4);
	      break;
	    }
	  /* Fall through.  */

	default:
	  /* This isn't a BAD_CASE, because presumably we can get here
	     from unexpected operands.  Since we don't handle them, make
	     them syntax errors.  */
	  as_bad_where (fixP->fx_file, fixP->fx_line,
			_("invalid expression in operand"));
	}
      fixP->fx_done = 1;
    }
}

/* Hook called from md_convert_frag in tc-sh.c.  */

static void
shmedia_md_convert_frag (bfd *output_bfd ATTRIBUTE_UNUSED,
			 segT seg ATTRIBUTE_UNUSED, fragS *fragP,
			 bfd_boolean final)
{
  /* Pointer to first byte in variable-sized part of the frag.	*/
  char *var_partp;

  /* Pointer to first opcode byte in frag.  */
  char *opcodep;

  /* Pointer to frag of opcode.  */
  fragS *opc_fragP = fragP->tc_frag_data.opc_frag;

  /* Size in bytes of variable-sized part of frag.  */
  int var_part_size = 0;

  /* This is part of *fragP.  It contains all information about addresses
     and offsets to varying parts.  */
  symbolS *symbolP = fragP->fr_symbol;

  bfd_boolean reloc_needed
    = (! final
       || sh_relax
       || symbolP == NULL
       || ! S_IS_DEFINED (symbolP)
       || S_IS_EXTERNAL (symbolP)
       || S_IS_WEAK (symbolP)
       || (S_GET_SEGMENT (fragP->fr_symbol) != absolute_section
	   && S_GET_SEGMENT (fragP->fr_symbol) != seg));

  bfd_reloc_code_real_type reloctype = BFD_RELOC_NONE;

  unsigned long var_part_offset;

  /* Where, in file space, does addr point?  */
  bfd_vma target_address;
  bfd_vma opcode_address;

  /* What was the insn?  */
  unsigned long insn;
  know (fragP->fr_type == rs_machine_dependent);

  var_part_offset = fragP->fr_fix;
  var_partp = fragP->fr_literal + var_part_offset;
  opcodep = fragP->fr_opcode;

  insn = target_big_endian ? bfd_getb32 (opcodep) : bfd_getl32 (opcodep);

  target_address
    = ((symbolP && final && ! sh_relax ? S_GET_VALUE (symbolP) : 0)
       + fragP->fr_offset);

  /* The opcode that would be extended is the last four "fixed" bytes.  */
  opcode_address = fragP->fr_address + fragP->fr_fix - 4;

  switch (fragP->fr_subtype)
    {
    case C (SH64PCREL16PT_64, SH64PCREL16):
    case C (SH64PCREL16PT_32, SH64PCREL16):
      /* We can get a PT to a relaxed SHcompact address if it is in the
	 same section; a mixed-ISA section.  Change the opcode to PTB if
	 so.  */
      if ((target_address & 1) == 0)
	insn |= SHMEDIA_PTB_BIT;
      /* Fall through.  */

    case C (SH64PCREL16_32, SH64PCREL16):
    case C (SH64PCREL16_64, SH64PCREL16):
      /* Check that a PTA or PTB points to the right type of target.  We
	 can get here for a SHcompact target if we are in a mixed-ISA
	 section.  */
      if (((target_address & 1) == 0) && ((insn & SHMEDIA_PTB_BIT) == 0))
	as_bad_where (fragP->fr_file, fragP->fr_line,
		      _("PTA operand is a SHcompact symbol"));
      if (((target_address & 1) != 0) && ((insn & SHMEDIA_PTB_BIT) != 0))
	as_bad_where (fragP->fr_file, fragP->fr_line,
		      _("PTB operand is a SHmedia symbol"));

      /* When relaxing, we do not output the address in the insn, but
	 instead a 1 into the low bit.  This matches what the linker
	 expects to find for a BFD_RELOC_SH_PT_16 reloc, when it checks
	 correctness for PTA/PTB insn; used when the target address is
	 unknown (which is not the case here).  */
      md_number_to_chars (opcodep,
			  insn
			  | (((sh_relax
			       ? 1 : ((target_address - opcode_address) / 4))
			      & ((1 << 16) - 1)) << 10),
			  4);

      /* Note that we do not emit info that this was originally a PT since
	 we have resolved to which one of PTA or PTB it will be.  */
      if (sh_relax)
	fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		 fragP->fr_symbol, fragP->fr_offset, 1, BFD_RELOC_SH_PT_16);
      var_part_size = 0;
      break;

    case C (SH64PCREL16_32, SH64PCRELPLT):
    case C (SH64PCREL16PT_32, SH64PCRELPLT):
      reloctype = BFD_RELOC_32_PLT_PCREL;
      reloc_needed = 1;
      /* Fall through */

    case C (SH64PCREL16_32, SH64PCREL32):
    case C (SH64PCREL16_64, SH64PCREL32):
    case C (SH64PCREL16PT_32, SH64PCREL32):
    case C (SH64PCREL16PT_64, SH64PCREL32):
      /* In the fixed bit, put in a MOVI.  */
      md_number_to_chars (opcodep,
			  SHMEDIA_MOVI_OPC
			  | (SHMEDIA_TEMP_REG << 4)
			  | ((((reloc_needed
				? 0 : (target_address - (opcode_address + 8))
				) >> 16) & 65535) << 10),
			  4);

      /* Fill in a SHORI for the low part.  */
      md_number_to_chars (var_partp,
			  SHMEDIA_SHORI_OPC
			  | (SHMEDIA_TEMP_REG << 4)
			  | (((reloc_needed
			       ? 0 : (target_address - (opcode_address + 8)))
			      & 65535) << 10),
			  4);

      /* End with a "PTREL R25,TRd".  */
      md_number_to_chars (var_partp + 4,
			  SHMEDIA_PTREL_OPC | (insn & SHMEDIA_LIKELY_BIT)
			  | (SHMEDIA_TEMP_REG << 10)
			  | (insn & (7 << 4)),
			  4);

      /* We need relocs only if the target symbol was undefined or if
	 we're relaxing.  */
      if (reloc_needed)
	{
	  fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		   fragP->fr_symbol, fragP->fr_offset - 8, 1,
		   reloctype == BFD_RELOC_32_PLT_PCREL
		   ? BFD_RELOC_SH_PLT_MEDLOW16
		   : BFD_RELOC_SH_IMM_MEDLOW16_PCREL);
	  fix_new (fragP, var_partp - fragP->fr_literal, 4, fragP->fr_symbol,
		   fragP->fr_offset - 4, 1,
		   reloctype == BFD_RELOC_32_PLT_PCREL
		   ? BFD_RELOC_SH_PLT_LOW16
		   : BFD_RELOC_SH_IMM_LOW16_PCREL);
	}

      var_part_size = 8;
      break;

    case C (SH64PCREL16_64, SH64PCREL48):
    case C (SH64PCREL16PT_64, SH64PCREL48):
      /* In the fixed bit, put in a MOVI.  */
      md_number_to_chars (opcodep,
			  SHMEDIA_MOVI_OPC
			  | (SHMEDIA_TEMP_REG << 4)
			  | ((((reloc_needed
				? 0 : (target_address - (opcode_address + 12))
				) >> 32) & 65535) << 10),
			  4);

      /* The first SHORI, for the medium part.  */
      md_number_to_chars (var_partp,
			  SHMEDIA_SHORI_OPC
			  | (SHMEDIA_TEMP_REG << 4)
			  | ((((reloc_needed
				? 0 : (target_address - (opcode_address + 12))
				) >> 16) & 65535) << 10),
			  4);

      /* Fill in a SHORI for the low part.  */
      md_number_to_chars (var_partp + 4,
			  SHMEDIA_SHORI_OPC
			  | (SHMEDIA_TEMP_REG << 4)
			  | (((reloc_needed
			       ? 0 : (target_address - (opcode_address + 12)))
			      & 65535) << 10),
			  4);

      /* End with a "PTREL R25,TRd".  */
      md_number_to_chars (var_partp + 8,
			  SHMEDIA_PTREL_OPC | (insn & SHMEDIA_LIKELY_BIT)
			  | (SHMEDIA_TEMP_REG << 10)
			  | (insn & (7 << 4)),
			  4);

      /* We need relocs only if the target symbol was undefined or if
	 we're relaxing.  */
      if (reloc_needed)
	{
	  fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		   fragP->fr_symbol, fragP->fr_offset - 12, 1,
		   reloctype == BFD_RELOC_32_PLT_PCREL
		   ? BFD_RELOC_SH_PLT_MEDHI16
		   : BFD_RELOC_SH_IMM_MEDHI16_PCREL);
	  fix_new (fragP, var_partp - fragP->fr_literal, 4, fragP->fr_symbol,
		   fragP->fr_offset - 8, 1,
		   reloctype == BFD_RELOC_32_PLT_PCREL
		   ? BFD_RELOC_SH_PLT_MEDLOW16
		   : BFD_RELOC_SH_IMM_MEDLOW16_PCREL);
	  fix_new (fragP, var_partp - fragP->fr_literal + 4, 4, fragP->fr_symbol,
		   fragP->fr_offset - 4, 1,
		   reloctype == BFD_RELOC_32_PLT_PCREL
		   ? BFD_RELOC_SH_PLT_LOW16
		   : BFD_RELOC_SH_IMM_LOW16_PCREL);
	}

      var_part_size = 12;
      break;

    case C (SH64PCREL16_64, SH64PCRELPLT):
    case C (SH64PCREL16PT_64, SH64PCRELPLT):
      reloctype = BFD_RELOC_32_PLT_PCREL;
      reloc_needed = 1;
      /* Fall through */

    case C (SH64PCREL16_64, SH64PCREL64):
    case C (SH64PCREL16PT_64, SH64PCREL64):
      /* In the fixed bit, put in a MOVI.  */
      md_number_to_chars (opcodep,
			  SHMEDIA_MOVI_OPC
			  | (SHMEDIA_TEMP_REG << 4)
			  | ((((reloc_needed
				? 0 : (target_address - (opcode_address + 16))
				) >> 48) & 65535) << 10),
			  4);

      /* The first SHORI, for the medium-high part.  */
      md_number_to_chars (var_partp,
			  SHMEDIA_SHORI_OPC
			  | (SHMEDIA_TEMP_REG << 4)
			  | ((((reloc_needed
				? 0 : (target_address - (opcode_address + 16))
				) >> 32) & 65535) << 10),
			  4);

      /* A SHORI, for the medium-low part.  */
      md_number_to_chars (var_partp + 4,
			  SHMEDIA_SHORI_OPC
			  | (SHMEDIA_TEMP_REG << 4)
			  | ((((reloc_needed
				? 0 : (target_address - (opcode_address + 16))
				) >> 16) & 65535) << 10),
			  4);

      /* Fill in a SHORI for the low part.  */
      md_number_to_chars (var_partp + 8,
			  SHMEDIA_SHORI_OPC
			  | (SHMEDIA_TEMP_REG << 4)
			  | (((reloc_needed
			       ? 0 : (target_address - (opcode_address + 16)))
			      & 65535) << 10),
			  4);

      /* End with a "PTREL R25,TRd".  */
      md_number_to_chars (var_partp + 12,
			  SHMEDIA_PTREL_OPC | (insn & SHMEDIA_LIKELY_BIT)
			  | (SHMEDIA_TEMP_REG << 10)
			  | (insn & (7 << 4)),
			  4);

      /* We need relocs only if the target symbol was undefined or if
	 we're relaxing.  */
      if (reloc_needed)
	{
	  fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		   fragP->fr_symbol, fragP->fr_offset - 16, 1,
		   reloctype == BFD_RELOC_32_PLT_PCREL
		   ? BFD_RELOC_SH_PLT_HI16
		   : BFD_RELOC_SH_IMM_HI16_PCREL);
	  fix_new (fragP, var_partp - fragP->fr_literal, 4, fragP->fr_symbol,
		   fragP->fr_offset - 12, 1,
		   reloctype == BFD_RELOC_32_PLT_PCREL
		   ? BFD_RELOC_SH_PLT_MEDHI16
		   : BFD_RELOC_SH_IMM_MEDHI16_PCREL);
	  fix_new (fragP, var_partp - fragP->fr_literal + 4, 4, fragP->fr_symbol,
		   fragP->fr_offset - 8, 1,
		   reloctype == BFD_RELOC_32_PLT_PCREL
		   ? BFD_RELOC_SH_PLT_MEDLOW16
		   : BFD_RELOC_SH_IMM_MEDLOW16_PCREL);
	  fix_new (fragP, var_partp - fragP->fr_literal + 8, 4, fragP->fr_symbol,
		   fragP->fr_offset - 4, 1,
		   reloctype == BFD_RELOC_32_PLT_PCREL
		   ? BFD_RELOC_SH_PLT_LOW16
		   : BFD_RELOC_SH_IMM_LOW16_PCREL);
	}

      var_part_size = 16;
      break;

    case C (MOVI_IMM_64, MOVI_GOTOFF):
      reloctype = BFD_RELOC_32_GOTOFF;
      reloc_needed = 1;
      /* Fall through.  */

    case C (MOVI_IMM_64, UNDEF_MOVI):
    case C (MOVI_IMM_64, MOVI_64):
      {
	/* We only get here for undefined symbols, so we can simplify
	   handling compared to those above; we have 0 in the parts that
	   will be filled with the symbol parts.  */

	int reg = (insn >> 4) & 0x3f;

	/* In the fixed bit, put in a MOVI.  */
	md_number_to_chars (opcodep, SHMEDIA_MOVI_OPC | (reg << 4), 4);
	fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		 fragP->fr_symbol, fragP->fr_offset, 0,
		 reloctype == BFD_RELOC_NONE
		 ? BFD_RELOC_SH_IMM_HI16
		 : reloctype == BFD_RELOC_32_GOTOFF
		 ? BFD_RELOC_SH_GOTOFF_HI16
		 : (abort (), BFD_RELOC_SH_IMM_HI16));

	/* The first SHORI, for the medium-high part.  */
	md_number_to_chars (var_partp, SHMEDIA_SHORI_OPC | (reg << 4), 4);
	fix_new (fragP, var_partp - fragP->fr_literal, 4, fragP->fr_symbol,
		 fragP->fr_offset, 0,
		 reloctype == BFD_RELOC_NONE
		 ? BFD_RELOC_SH_IMM_MEDHI16
		 : reloctype == BFD_RELOC_32_GOTOFF
		 ? BFD_RELOC_SH_GOTOFF_MEDHI16
		 : (abort (), BFD_RELOC_SH_IMM_MEDHI16));

	/* A SHORI, for the medium-low part.  */
	md_number_to_chars (var_partp + 4,
			    SHMEDIA_SHORI_OPC | (reg << 4), 4);
	fix_new (fragP, var_partp - fragP->fr_literal + 4, 4, fragP->fr_symbol,
		 fragP->fr_offset, 0,
		 reloctype == BFD_RELOC_NONE
		 ? BFD_RELOC_SH_IMM_MEDLOW16
		 : reloctype == BFD_RELOC_32_GOTOFF
		 ? BFD_RELOC_SH_GOTOFF_MEDLOW16
		 : (abort (), BFD_RELOC_SH_IMM_MEDLOW16));

	/* Fill in a SHORI for the low part.  */
	md_number_to_chars (var_partp + 8,
			    SHMEDIA_SHORI_OPC | (reg << 4), 4);
	fix_new (fragP, var_partp - fragP->fr_literal + 8, 4, fragP->fr_symbol,
		 fragP->fr_offset, 0,
		 reloctype == BFD_RELOC_NONE
		 ? BFD_RELOC_SH_IMM_LOW16
		 : reloctype == BFD_RELOC_32_GOTOFF
		 ? BFD_RELOC_SH_GOTOFF_LOW16
		 : (abort (), BFD_RELOC_SH_IMM_LOW16));

	var_part_size = 12;
	break;
      }

    case C (MOVI_IMM_32, MOVI_GOTOFF):
      reloctype = BFD_RELOC_32_GOTOFF;
      reloc_needed = 1;
      /* Fall through.  */

    case C (MOVI_IMM_32, UNDEF_MOVI):
    case C (MOVI_IMM_32, MOVI_32):
      {
	/* Note that we only get here for undefined symbols.  */

	int reg = (insn >> 4) & 0x3f;

	/* A MOVI, for the high part.  */
	md_number_to_chars (opcodep, SHMEDIA_MOVI_OPC | (reg << 4), 4);
	fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		 fragP->fr_symbol, fragP->fr_offset, 0,
		 reloctype == BFD_RELOC_NONE
		 ? BFD_RELOC_SH_IMM_MEDLOW16
		 : reloctype == BFD_RELOC_32_GOTOFF
		 ? BFD_RELOC_SH_GOTOFF_MEDLOW16
		 : reloctype == BFD_RELOC_SH_GOTPC
		 ? BFD_RELOC_SH_GOTPC_MEDLOW16
		 : reloctype == BFD_RELOC_32_PLT_PCREL
		 ? BFD_RELOC_SH_PLT_MEDLOW16
		 : (abort (), BFD_RELOC_SH_IMM_MEDLOW16));

	/* Fill in a SHORI for the low part.  */
	md_number_to_chars (var_partp,
			    SHMEDIA_SHORI_OPC | (reg << 4), 4);
	fix_new (fragP, var_partp - fragP->fr_literal, 4, fragP->fr_symbol,
		 fragP->fr_offset, 0,
		 reloctype == BFD_RELOC_NONE
		 ? BFD_RELOC_SH_IMM_LOW16
		 : reloctype == BFD_RELOC_32_GOTOFF
		 ? BFD_RELOC_SH_GOTOFF_LOW16
		 : reloctype == BFD_RELOC_SH_GOTPC
		 ? BFD_RELOC_SH_GOTPC_LOW16
		 : reloctype == BFD_RELOC_32_PLT_PCREL
		 ? BFD_RELOC_SH_PLT_LOW16
		 : (abort (), BFD_RELOC_SH_IMM_LOW16));

	var_part_size = 4;
	break;
      }

    case C (MOVI_IMM_32_PCREL, MOVI_16):
    case C (MOVI_IMM_64_PCREL, MOVI_16):
      md_number_to_chars (opcodep,
			  insn
			  | (((reloc_needed
			       ? 0 : (target_address - opcode_address))
			      & 65535) << 10),
			  4);
      if (reloc_needed)
	fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		 fragP->fr_symbol, fragP->fr_offset, 1,
		 BFD_RELOC_SH_IMM_LOW16_PCREL);
      var_part_size = 0;
      break;

    case C (MOVI_IMM_32, MOVI_16):
    case C (MOVI_IMM_64, MOVI_16):
      md_number_to_chars (opcodep,
			  insn
			  | (((reloc_needed ? 0 : target_address)
			      & 65535) << 10),
			  4);
      if (reloc_needed)
	abort ();
      var_part_size = 0;
      break;

    case C (MOVI_IMM_32_PCREL, MOVI_PLT):
      reloctype = BFD_RELOC_32_PLT_PCREL;
      goto movi_imm_32_pcrel_reloc_needed;

    case C (MOVI_IMM_32_PCREL, MOVI_GOTPC):
      reloctype = BFD_RELOC_SH_GOTPC;
      /* Fall through.  */

    movi_imm_32_pcrel_reloc_needed:
      reloc_needed = 1;
      /* Fall through.  */

    case C (MOVI_IMM_32_PCREL, MOVI_32):
    case C (MOVI_IMM_64_PCREL, MOVI_32):
      {
	int reg = (insn >> 4) & 0x3f;

	md_number_to_chars (opcodep,
			    insn
			    | (((((reloc_needed
				   ? 0 : (target_address - opcode_address)))
				>> 16) & 65535) << 10), 4);

	/* A SHORI, for the low part.  */
	md_number_to_chars (var_partp,
			    SHMEDIA_SHORI_OPC
			    | (reg << 4)
			    | (((reloc_needed
				 ? 0 : (target_address - opcode_address))
				& 65535) << 10), 4);
	if (reloc_needed)
	  {
	    fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		     fragP->fr_symbol, fragP->fr_offset, 1,
		     reloctype == BFD_RELOC_NONE
		     ? BFD_RELOC_SH_IMM_MEDLOW16_PCREL
		     : reloctype == BFD_RELOC_SH_GOTPC
		     ? BFD_RELOC_SH_GOTPC_MEDLOW16
		     : reloctype == BFD_RELOC_32_PLT_PCREL
		     ? BFD_RELOC_SH_PLT_MEDLOW16
		     : (abort (), BFD_RELOC_SH_IMM_MEDLOW16_PCREL));
	    fix_new (fragP, var_partp - fragP->fr_literal, 4, fragP->fr_symbol,
		     fragP->fr_offset + 4, 1,
		     reloctype == BFD_RELOC_NONE
		     ? BFD_RELOC_SH_IMM_LOW16_PCREL
		     : reloctype == BFD_RELOC_SH_GOTPC
		     ? BFD_RELOC_SH_GOTPC_LOW16
		     : reloctype == BFD_RELOC_32_PLT_PCREL
		     ? BFD_RELOC_SH_PLT_LOW16
		     : (abort (), BFD_RELOC_SH_IMM_LOW16_PCREL));
	  }
	var_part_size = 4;
      }
      break;

    case C (MOVI_IMM_32_PCREL, MOVI_48):
    case C (MOVI_IMM_64_PCREL, MOVI_48):
      {
	int reg = (insn >> 4) & 0x3f;

	md_number_to_chars (opcodep,
			    insn
			    | (((((reloc_needed
				   ? 0 : (target_address - opcode_address)))
				>> 32) & 65535) << 10), 4);

	/* A SHORI, for the medium part.  */
	md_number_to_chars (var_partp,
			    SHMEDIA_SHORI_OPC
			    | (reg << 4)
			    | ((((reloc_needed
				  ? 0 : (target_address - opcode_address))
				 >> 16) & 65535) << 10), 4);

	/* A SHORI, for the low part.  */
	md_number_to_chars (var_partp + 4,
			    SHMEDIA_SHORI_OPC
			    | (reg << 4)
			    | (((reloc_needed
				 ? 0 : (target_address - opcode_address))
				& 65535) << 10), 4);
	if (reloc_needed)
	  {
	    fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		     fragP->fr_symbol, fragP->fr_offset, 1,
		     BFD_RELOC_SH_IMM_MEDHI16_PCREL);
	    fix_new (fragP, var_partp - fragP->fr_literal, 4, fragP->fr_symbol,
		     fragP->fr_offset + 4, 1, BFD_RELOC_SH_IMM_MEDLOW16_PCREL);
	    fix_new (fragP, var_partp - fragP->fr_literal + 4, 4, fragP->fr_symbol,
		     fragP->fr_offset + 8, 1, BFD_RELOC_SH_IMM_LOW16_PCREL);
	  }
	var_part_size = 8;
      }
      break;

    case C (MOVI_IMM_64_PCREL, MOVI_PLT):
      reloctype = BFD_RELOC_32_PLT_PCREL;
      goto movi_imm_64_pcrel_reloc_needed;

    case C (MOVI_IMM_64_PCREL, MOVI_GOTPC):
      reloctype = BFD_RELOC_SH_GOTPC;
      /* Fall through.  */

    movi_imm_64_pcrel_reloc_needed:
      reloc_needed = 1;
      /* Fall through.  */

    case C (MOVI_IMM_32_PCREL, MOVI_64):
    case C (MOVI_IMM_64_PCREL, MOVI_64):
      {
	int reg = (insn >> 4) & 0x3f;

	md_number_to_chars (opcodep,
			    insn
			    | (((((reloc_needed
				   ? 0 : (target_address - opcode_address)))
				>> 48) & 65535) << 10), 4);

	/* A SHORI, for the medium-high part.  */
	md_number_to_chars (var_partp,
			    SHMEDIA_SHORI_OPC
			    | (reg << 4)
			    | ((((reloc_needed
				  ? 0 : (target_address - opcode_address))
				 >> 32) & 65535) << 10), 4);

	/* A SHORI, for the medium-low part.  */
	md_number_to_chars (var_partp + 4,
			    SHMEDIA_SHORI_OPC
			    | (reg << 4)
			    | ((((reloc_needed
				  ? 0 : (target_address - opcode_address))
				 >> 16) & 65535) << 10), 4);

	/* A SHORI, for the low part.  */
	md_number_to_chars (var_partp + 8,
			    SHMEDIA_SHORI_OPC
			    | (reg << 4)
			    | (((reloc_needed
				 ? 0 : (target_address - opcode_address))
				& 65535) << 10), 4);
	if (reloc_needed)
	  {
	    fix_new (opc_fragP, opcodep - opc_fragP->fr_literal, 4,
		     fragP->fr_symbol, fragP->fr_offset, 1,
		     reloctype == BFD_RELOC_NONE
		     ? BFD_RELOC_SH_IMM_HI16_PCREL
		     : reloctype == BFD_RELOC_SH_GOTPC
		     ? BFD_RELOC_SH_GOTPC_HI16
		     : reloctype == BFD_RELOC_32_PLT_PCREL
		     ? BFD_RELOC_SH_PLT_HI16
		     : (abort (), BFD_RELOC_SH_IMM_HI16_PCREL));
	    fix_new (fragP, var_partp - fragP->fr_literal, 4, fragP->fr_symbol,
		     fragP->fr_offset + 4, 1,
		     reloctype == BFD_RELOC_NONE
		     ? BFD_RELOC_SH_IMM_MEDHI16_PCREL
		     : reloctype == BFD_RELOC_SH_GOTPC
		     ? BFD_RELOC_SH_GOTPC_MEDHI16
		     : reloctype == BFD_RELOC_32_PLT_PCREL
		     ? BFD_RELOC_SH_PLT_MEDHI16
		     : (abort (), BFD_RELOC_SH_IMM_MEDHI16_PCREL));
	    fix_new (fragP, var_partp - fragP->fr_literal + 4, 4,
		     fragP->fr_symbol,
		     fragP->fr_offset + 8, 1,
		     reloctype == BFD_RELOC_NONE
		     ? BFD_RELOC_SH_IMM_MEDLOW16_PCREL
		     : reloctype == BFD_RELOC_SH_GOTPC
		     ? BFD_RELOC_SH_GOTPC_MEDLOW16
		     : reloctype == BFD_RELOC_32_PLT_PCREL
		     ? BFD_RELOC_SH_PLT_MEDLOW16
		     : (abort (), BFD_RELOC_SH_IMM_MEDLOW16_PCREL));
	    fix_new (fragP, var_partp - fragP->fr_literal + 8, 4,
		     fragP->fr_symbol,
		     fragP->fr_offset + 12, 1,
		     reloctype == BFD_RELOC_NONE
		     ? BFD_RELOC_SH_IMM_LOW16_PCREL
		     : reloctype == BFD_RELOC_SH_GOTPC
		     ? BFD_RELOC_SH_GOTPC_LOW16
		     : reloctype == BFD_RELOC_32_PLT_PCREL
		     ? BFD_RELOC_SH_PLT_LOW16
		     : (abort (), BFD_RELOC_SH_IMM_LOW16_PCREL));
	  }
	var_part_size = 12;
      }
      break;

    default:
      BAD_CASE (fragP->fr_subtype);
    }

  fragP->fr_fix += var_part_size;
  fragP->fr_var = 0;
}

/* Mask NUMBER (originating from a signed number) corresponding to the HOW
   reloc.  */

static unsigned long
shmedia_mask_number (unsigned long number, bfd_reloc_code_real_type how)
{
  switch (how)
    {
    case BFD_RELOC_SH_IMMU5:
      number &= (1 << 5) - 1;
      break;

    case BFD_RELOC_SH_IMMS6:
    case BFD_RELOC_SH_IMMU6:
      number &= (1 << 6) - 1;
      break;

    case BFD_RELOC_SH_IMMS6BY32:
      number = (number & ((1 << (6 + 5)) - 1)) >> 5;
      break;

    case BFD_RELOC_SH_IMMS10:
      number &= (1 << 10) - 1;
      break;

    case BFD_RELOC_SH_IMMS10BY2:
      number = (number & ((1 << (10 + 1)) - 1)) >> 1;
      break;

    case BFD_RELOC_SH_IMMS10BY4:
      number = (number & ((1 << (10 + 2)) - 1)) >> 2;
      break;

    case BFD_RELOC_SH_IMMS10BY8:
      number = (number & ((1 << (10 + 3)) - 1)) >> 3;
      break;

    case BFD_RELOC_SH_IMMS16:
    case BFD_RELOC_SH_IMMU16:
      number &= (1 << 16) - 1;
      break;

    default:
      BAD_CASE (how);
    }

  return number;
}

/* Emit errors for values out-of-range, using as_bad_where if FRAGP is
   non-NULL, as_bad otherwise.  */

static void
shmedia_check_limits (offsetT *valp, bfd_reloc_code_real_type reloc,
		      fixS *fixp)
{
  offsetT val = *valp;

  char *msg = NULL;

  switch (reloc)
    {
    case BFD_RELOC_SH_IMMU5:
      if (val < 0 || val > (1 << 5) - 1)
	msg = _("invalid operand, not a 5-bit unsigned value: %d");
      break;

    case BFD_RELOC_SH_IMMS6:
      if (val < -(1 << 5) || val > (1 << 5) - 1)
	msg = _("invalid operand, not a 6-bit signed value: %d");
      break;

    case BFD_RELOC_SH_IMMU6:
      if (val < 0 || val > (1 << 6) - 1)
	msg = _("invalid operand, not a 6-bit unsigned value: %d");
      break;

    case BFD_RELOC_SH_IMMS6BY32:
      if (val < -(1 << 10) || val > (1 << 10) - 1)
	msg = _("invalid operand, not a 11-bit signed value: %d");
      else if (val & 31)
	msg = _("invalid operand, not a multiple of 32: %d");
      break;

    case BFD_RELOC_SH_IMMS10:
      if (val < -(1 << 9) || val > (1 << 9) - 1)
	msg = _("invalid operand, not a 10-bit signed value: %d");
      break;

    case BFD_RELOC_SH_IMMS10BY2:
      if (val < -(1 << 10) || val > (1 << 10) - 1)
	msg = _("invalid operand, not a 11-bit signed value: %d");
      else if (val & 1)
	msg = _("invalid operand, not an even value: %d");
      break;

    case BFD_RELOC_SH_IMMS10BY4:
      if (val < -(1 << 11) || val > (1 << 11) - 1)
	msg = _("invalid operand, not a 12-bit signed value: %d");
      else if (val & 3)
	msg = _("invalid operand, not a multiple of 4: %d");
      break;

    case BFD_RELOC_SH_IMMS10BY8:
      if (val < -(1 << 12) || val > (1 << 12) - 1)
	msg = _("invalid operand, not a 13-bit signed value: %d");
      else if (val & 7)
	msg = _("invalid operand, not a multiple of 8: %d");
      break;

    case BFD_RELOC_SH_IMMS16:
      if (val < -(1 << 15) || val > (1 << 15) - 1)
	msg = _("invalid operand, not a 16-bit signed value: %d");
      break;

    case BFD_RELOC_SH_IMMU16:
      if (val < 0 || val > (1 << 16) - 1)
	msg = _("invalid operand, not a 16-bit unsigned value: %d");
      break;

    case BFD_RELOC_SH_PT_16:
    case SHMEDIA_BFD_RELOC_PT:
      if (val < -(1 << 15) * 4 || val > ((1 << 15) - 1) * 4 + 1)
	msg = _("operand out of range for PT, PTA and PTB");
      else if ((val % 4) != 0 && ((val - 1) % 4) != 0)
	msg = _("operand not a multiple of 4 for PT, PTA or PTB: %d");
      break;

      /* These have no limits; they take a 16-bit slice of a 32- or 64-bit
	 number.  */
    case BFD_RELOC_SH_IMM_HI16:
    case BFD_RELOC_SH_IMM_MEDHI16:
    case BFD_RELOC_SH_IMM_MEDLOW16:
    case BFD_RELOC_SH_IMM_LOW16:
    case BFD_RELOC_SH_IMM_HI16_PCREL:
    case BFD_RELOC_SH_IMM_MEDHI16_PCREL:
    case BFD_RELOC_SH_IMM_MEDLOW16_PCREL:
    case BFD_RELOC_SH_IMM_LOW16_PCREL:

    case BFD_RELOC_SH_SHMEDIA_CODE:
      break;

      /* This one has limits out of our reach.  */
    case BFD_RELOC_64:
      break;

    default:
      BAD_CASE (reloc);
    }

  if (msg)
    {
      if (fixp)
	as_bad_where (fixp->fx_file, fixp->fx_line, msg, val);
      else
	as_bad (msg, val);
    }
}

/* Handle an immediate operand by checking limits and noting it for later
   evaluation if not computable yet, and return a bitfield suitable to
   "or" into the opcode (non-zero if the value was a constant number).  */

static unsigned long
shmedia_immediate_op (char *where, shmedia_operand_info *op, int pcrel,
		      bfd_reloc_code_real_type how)
{
  unsigned long retval = 0;

  /* If this is not an absolute number, make it a fixup.  A constant in
     place of a pc-relative operand also needs a fixup.  */
  if (op->immediate.X_op != O_constant || pcrel)
    fix_new_exp (frag_now,
		 where - frag_now->fr_literal,
		 4,
		 &op->immediate,
		 pcrel,
		 how);
  else
    {
      /* Check that the number is within limits as represented by the
	 reloc, and return the number.  */
      shmedia_check_limits (&op->immediate.X_add_number, how, NULL);

      retval
	= shmedia_mask_number ((unsigned long) op->immediate.X_add_number,
			       how);
    }

  return retval << 10;
}

/* Try and parse a register name case-insensitively, return the number of
   chars consumed.  */

static int
shmedia_parse_reg (char *src, int *mode, int *reg, shmedia_arg_type argtype)
{
  int l0 = TOLOWER (src[0]);
  int l1 = l0 ? TOLOWER (src[1]) : 0;

  if (l0 == 'r')
    {
      if (src[1] >= '1' && src[1] <= '5')
	{
	  if (src[2] >= '0' && src[2] <= '9'
	      && ! IDENT_CHAR ((unsigned char) src[3]))
	    {
	      *mode = A_GREG_M;
	      *reg = 10 * (src[1] - '0') + src[2] - '0';
	      return 3;
	    }
	}

      if (src[1] == '6')
	{
	  if (src[2] >= '0' && src[2] <= '3'
	      && ! IDENT_CHAR ((unsigned char) src[3]))
	    {
	      *mode = A_GREG_M;
	      *reg = 60 + src[2] - '0';
	      return 3;
	    }
	}

      if (src[1] >= '0' && src[1] <= '9'
	  && ! IDENT_CHAR ((unsigned char) src[2]))
	{
	  *mode = A_GREG_M;
	  *reg = (src[1] - '0');
	  return 2;
	}
    }

  if (l0 == 't' && l1 == 'r')
    {
      if (src[2] >= '0' && src[2] <= '7'
	  && ! IDENT_CHAR ((unsigned char) src[3]))
	{
	  *mode = A_TREG_B;
	  *reg = (src[2] - '0');
	  return 3;
	}
    }

  if (l0 == 'f' && l1 == 'r')
    {
      if (src[2] >= '1' && src[2] <= '5')
	{
	  if (src[3] >= '0' && src[3] <= '9'
	      && ! IDENT_CHAR ((unsigned char) src[4]))
	    {
	      *mode = A_FREG_G;
	      *reg = 10 * (src[2] - '0') + src[3] - '0';
	      return 4;
	    }
	}
      if (src[2] == '6')
	{
	  if (src[3] >= '0' && src[3] <= '3'
	      && ! IDENT_CHAR ((unsigned char) src[4]))
	    {
	      *mode = A_FREG_G;
	      *reg = 60 + src[3] - '0';
	      return 4;
	    }
	}
      if (src[2] >= '0' && src[2] <= '9'
	  && ! IDENT_CHAR ((unsigned char) src[3]))
	{
	  *mode = A_FREG_G;
	  *reg = (src[2] - '0');
	  return 3;
	}
    }

  if (l0 == 'f' && l1 == 'v')
    {
      if (src[2] >= '1' && src[2] <= '5')
	{
	  if (src[3] >= '0' && src[3] <= '9'
	      && ((10 * (src[2] - '0') + src[3] - '0') % 4) == 0
	      && ! IDENT_CHAR ((unsigned char) src[4]))
	    {
	      *mode = A_FVREG_G;
	      *reg = 10 * (src[2] - '0') + src[3] - '0';
	      return 4;
	    }
	}
      if (src[2] == '6')
	{
	  if (src[3] == '0'
	      && ! IDENT_CHAR ((unsigned char) src[4]))
	    {
	      *mode = A_FVREG_G;
	      *reg = 60 + src[3] - '0';
	      return 4;
	    }
	}
      if (src[2] >= '0' && src[2] <= '9'
	  && ((src[2] - '0') % 4) == 0
	  && ! IDENT_CHAR ((unsigned char) src[3]))
	{
	  *mode = A_FVREG_G;
	  *reg = (src[2] - '0');
	  return 3;
	}
    }

  if (l0 == 'd' && l1 == 'r')
    {
      if (src[2] >= '1' && src[2] <= '5')
	{
	  if (src[3] >= '0' && src[3] <= '9'
	      && ((src[3] - '0') % 2) == 0
	      && ! IDENT_CHAR ((unsigned char) src[4]))
	    {
	      *mode = A_DREG_G;
	      *reg = 10 * (src[2] - '0') + src[3] - '0';
	      return 4;
	    }
	}

      if (src[2] == '6')
	{
	  if ((src[3] == '0' || src[3] == '2')
	      && ! IDENT_CHAR ((unsigned char) src[4]))
	    {
	      *mode = A_DREG_G;
	      *reg = 60 + src[3] - '0';
	      return 4;
	    }
	}

      if (src[2] >= '0' && src[2] <= '9'
	  && ((src[2] - '0') % 2) == 0
	  && ! IDENT_CHAR ((unsigned char) src[3]))
	{
	  *mode = A_DREG_G;
	  *reg = (src[2] - '0');
	  return 3;
	}
    }

  if (l0 == 'f' && l1 == 'p')
    {
      if (src[2] >= '1' && src[2] <= '5')
	{
	  if (src[3] >= '0' && src[3] <= '9'
	      && ((src[3] - '0') % 2) == 0
	      && ! IDENT_CHAR ((unsigned char) src[4]))
	    {
	      *mode = A_FPREG_G;
	      *reg = 10 * (src[2] - '0') + src[3] - '0';
	      return 4;
	    }
	}

      if (src[2] == '6')
	{
	  if ((src[3] == '0' || src[3] == '2')
	      && ! IDENT_CHAR ((unsigned char) src[4]))
	    {
	      *mode = A_FPREG_G;
	      *reg = 60 + src[3] - '0';
	      return 4;
	    }
	}

      if (src[2] >= '0' && src[2] <= '9'
	  && ((src[2] - '0') % 2) == 0
	  && ! IDENT_CHAR ((unsigned char) src[3]))
	{
	  *mode = A_FPREG_G;
	  *reg = (src[2] - '0');
	  return 3;
	}
    }

  if (l0 == 'm' && strncasecmp (src, "mtrx", 4) == 0)
    {
      if (src[4] == '0' && ! IDENT_CHAR ((unsigned char) src[5]))
	{
	  *mode = A_FMREG_G;
	  *reg = 0;
	  return 5;
	}

      if (src[4] == '1' && src[5] == '6'
	  && ! IDENT_CHAR ((unsigned char) src[6]))
	{
	  *mode = A_FMREG_G;
	  *reg = 16;
	  return 6;
	}

      if (src[4] == '3' && src[5] == '2'
	  && ! IDENT_CHAR ((unsigned char) src[6]))
	{
	  *mode = A_FMREG_G;
	  *reg = 32;
	  return 6;
	}

      if (src[4] == '4' && src[5] == '8'
	  && ! IDENT_CHAR ((unsigned char) src[6]))
	{
	  *mode = A_FMREG_G;
	  *reg = 48;
	  return 6;
	}
    }

  if (l0 == 'c' && l1 == 'r')
    {
      if (src[2] >= '1' && src[2] <= '5')
	{
	  if (src[3] >= '0' && src[3] <= '9'
	      && ! IDENT_CHAR ((unsigned char) src[4]))
	    {
	      *mode = A_CREG_K;
	      *reg = 10 * (src[2] - '0') + src[3] - '0';
	      return 4;
	    }
	}
      if (src[2] == '6')
	{
	  if (src[3] >= '0' && src[3] <= '3'
	      && ! IDENT_CHAR ((unsigned char) src[4]))
	    {
	      *mode = A_CREG_K;
	      *reg = 60 + src[3] - '0';
	      return 4;
	    }
	}
      if (src[2] >= '0' && src[2] <= '9'
	  && ! IDENT_CHAR ((unsigned char) src[3]))
	{
	  *mode = A_CREG_K;
	  *reg = (src[2] - '0');
	  return 3;
	}
    }

  /* We either have an error, a symbol or a control register by predefined
     name.  To keep things simple but still fast for normal cases, we do
     linear search in the (not to big) table of predefined control
     registers.  We only do this when we *expect* a control register.
     Those instructions should be rare enough that linear searching is ok.
     Or just read them into a hash-table in shmedia_md_begin.  Since they
     cannot be specified in the same place of symbol operands, don't add
     them there to the *main* symbol table as being in "reg_section".  */
  if (argtype == A_CREG_J || argtype == A_CREG_K)
    {
      const shmedia_creg_info *cregp;
      int len = 0;

      for (cregp = shmedia_creg_table; cregp->name != NULL; cregp++)
	{
	  len = strlen (cregp->name);
	  if (strncasecmp (cregp->name, src, len) == 0
	      && ! IDENT_CHAR (src[len]))
	    break;
	}

      if (cregp->name != NULL)
	{
	  *mode = A_CREG_K;
	  *reg = cregp->cregno;
	  return len;
	}
    }

  return 0;
}

/* Called from md_estimate_size_before_relax in tc-sh.c  */

static int
shmedia_md_estimate_size_before_relax (fragS *fragP,
				       segT segment_type ATTRIBUTE_UNUSED)
{
  int old_fr_fix;
  expressionS *exp;

  /* For ELF, we can't relax externally visible symbols; see tc-i386.c.  */
  bfd_boolean sym_relaxable
    = (fragP->fr_symbol
       && S_GET_SEGMENT (fragP->fr_symbol) == segment_type
       && ! S_IS_EXTERNAL (fragP->fr_symbol)
       && ! S_IS_WEAK (fragP->fr_symbol));

  old_fr_fix = fragP->fr_fix;

  switch (fragP->fr_subtype)
    {
    case C (SH64PCREL16_32, UNDEF_SH64PCREL):
    case C (SH64PCREL16PT_32, UNDEF_SH64PCREL):
      /* Used to be to somewhere which was unknown.  */
      if (sym_relaxable)
	{
	  int what = GET_WHAT (fragP->fr_subtype);

	  /* In this segment, so head for shortest.  */
	  fragP->fr_subtype = C (what, SH64PCREL16);
	}
      else
	{
	  int what = GET_WHAT (fragP->fr_subtype);
	  /* We know the abs value, but we don't know where we will be
	     linked, so we must make it the longest.  Presumably we could
	     switch to a non-pcrel representation, but having absolute
	     values in PT operands should be rare enough not to be worth
	     adding that code.  */
	  fragP->fr_subtype = C (what, SH64PCREL32);
	}
      fragP->fr_var = md_relax_table[fragP->fr_subtype].rlx_length;
      break;

    case C (SH64PCREL16_64, UNDEF_SH64PCREL):
    case C (SH64PCREL16PT_64, UNDEF_SH64PCREL):
      /* Used to be to somewhere which was unknown.  */
      if (sym_relaxable)
	{
	  int what = GET_WHAT (fragP->fr_subtype);

	  /* In this segment, so head for shortest.  */
	  fragP->fr_subtype = C (what, SH64PCREL16);
	}
      else
	{
	  int what = GET_WHAT (fragP->fr_subtype);
	  /* We know the abs value, but we don't know where we will be
	     linked, so we must make it the longest.  Presumably we could
	     switch to a non-pcrel representation, but having absolute
	     values in PT operands should be rare enough not to be worth
	     adding that code.  */
	  fragP->fr_subtype = C (what, SH64PCREL64);
	}
      fragP->fr_var = md_relax_table[fragP->fr_subtype].rlx_length;
      break;

    case C (MOVI_IMM_64, UNDEF_MOVI):
    case C (MOVI_IMM_32, UNDEF_MOVI):
      exp = NULL;

      /* Look inside the "symbol".  If we find a PC-relative expression,
	 change this to a PC-relative, relaxable expression.  */
      if (fragP->fr_symbol != NULL
	  && (exp = symbol_get_value_expression (fragP->fr_symbol)) != NULL
	  && exp->X_op == O_subtract
	  && exp->X_op_symbol != NULL
	  && S_GET_SEGMENT (exp->X_op_symbol) == segment_type)
	{
	  int what = GET_WHAT (fragP->fr_subtype);
	  int what_high = what == MOVI_IMM_32 ? MOVI_32 : MOVI_64;
	  expressionS *opexp
	    = symbol_get_value_expression (exp->X_op_symbol);
	  expressionS *addexp
	    = symbol_get_value_expression (exp->X_add_symbol);

	  /* Change the MOVI expression to the "X" in "X - Y" and subtract
	     Y:s offset to this location from X.  Note that we can only
	     allow an Y which is offset from this frag.  */
	  if (opexp != NULL
	      && addexp != NULL
	      && opexp->X_op == O_constant
	      && fragP == symbol_get_frag (exp->X_op_symbol))
	    {
	      /* At this point, before relaxing, the add-number of opexp
		 is the offset from the fr_fix part.  */
	      fragP->fr_offset
		= (exp->X_add_number
		   - (opexp->X_add_number - (fragP->fr_fix - 4)));
	      fragP->fr_symbol = exp->X_add_symbol;

	      what = what == MOVI_IMM_32
		? MOVI_IMM_32_PCREL : MOVI_IMM_64_PCREL;

	      /* Check the "X" symbol to estimate the size of this
		 PC-relative expression.  */
	      if (S_GET_SEGMENT (exp->X_add_symbol) == segment_type
		  && ! S_IS_EXTERNAL (exp->X_add_symbol)
		  && ! S_IS_WEAK (exp->X_add_symbol))
		fragP->fr_subtype = C (what, MOVI_16);
	      else
		fragP->fr_subtype = C (what, what_high);

	      /* This is now a PC-relative expression, fit to be relaxed.  */
	    }
	  else
	    fragP->fr_subtype = C (what, what_high);
	}
      else if (fragP->fr_symbol == NULL
	       || (S_GET_SEGMENT (fragP->fr_symbol) == absolute_section
		   && exp->X_op == O_constant))
	{
	  unsigned long insn
	    = (target_big_endian
	       ? bfd_getb32 (fragP->fr_opcode)
	       : bfd_getl32 (fragP->fr_opcode));
	  offsetT one = (offsetT) 1;
	  offsetT value = fragP->fr_offset
	    + (fragP->fr_symbol == NULL ? 0 : S_GET_VALUE (fragP->fr_symbol));

	  if (value >= ((offsetT) -1 << 15) && value < ((offsetT) 1 << 15))
	    {
	      /* Fits in 16-bit signed number.  */
	      int what = GET_WHAT (fragP->fr_subtype);
	      fragP->fr_subtype = C (what, MOVI_16);

	      /* Just "or" in the value.  */
	      md_number_to_chars (fragP->fr_opcode,
				  insn | ((value & ((1 << 16) - 1)) << 10),
				  4);
	    }
	  else if (value >= -(one << 31)
		   && (value < (one << 31)
		       || (sh64_abi == sh64_abi_32 && value < (one << 32))))
	    {
	      /* The value fits in a 32-bit signed number.  */
	      int reg = (insn >> 4) & 0x3f;

	      /* Just "or" in the high bits of the value, making the first
		 MOVI.  */
	      md_number_to_chars (fragP->fr_opcode,
				  insn
				  | (((value >> 16) & ((1 << 16) - 1)) << 10),
				  4);

	      /* Add a SHORI with the low bits.  Note that this insn lives
		 in the variable fragment part.  */
	      md_number_to_chars (fragP->fr_literal + old_fr_fix,
				  SHMEDIA_SHORI_OPC
				  | (reg << 4)
				  | ((value & ((1 << 16) - 1)) << 10),
				  4);

	      /* We took a piece of the variable part.  */
	      fragP->fr_fix += 4;
	    }
	  else if (GET_WHAT (fragP->fr_subtype) == MOVI_IMM_32)
	    {
	      /* Value out of range.  */
	      as_bad_where (fragP->fr_file, fragP->fr_line,
			    _("MOVI operand is not a 32-bit signed value: 0x%8x%08x"),
			    ((unsigned int) (value >> 32)
			     & (unsigned int) 0xffffffff),
			    (unsigned int) value & (unsigned int) 0xffffffff);

	      /* Must advance size, or we will get internal inconsistency
		 and fall into an assert.  */
	      fragP->fr_fix += 4;
	    }
	  /* Now we know we are allowed to expand to 48- and 64-bit values.  */
	  else if (value >= -(one << 47) && value < (one << 47))
	    {
	      /* The value fits in a 48-bit signed number.  */
	      int reg = (insn >> 4) & 0x3f;

	      /* Just "or" in the high bits of the value, making the first
		 MOVI.  */
	      md_number_to_chars (fragP->fr_opcode,
				  insn
				  | (((value >> 32) & ((1 << 16) - 1)) << 10),
				  4);

	      /* Add a SHORI with the middle bits.  Note that this insn lives
		 in the variable fragment part.  */
	      md_number_to_chars (fragP->fr_literal + old_fr_fix,
				  SHMEDIA_SHORI_OPC
				  | (reg << 4)
				  | (((value >> 16) & ((1 << 16) - 1)) << 10),
				  4);

	      /* Add a SHORI with the low bits.  */
	      md_number_to_chars (fragP->fr_literal + old_fr_fix + 4,
				  SHMEDIA_SHORI_OPC
				  | (reg << 4)
				  | ((value & ((1 << 16) - 1)) << 10),
				  4);

	      /* We took a piece of the variable part.  */
	      fragP->fr_fix += 8;
	    }
	  else
	    {
	      /* A 64-bit number.  */
	      int reg = (insn >> 4) & 0x3f;

	      /* Just "or" in the high bits of the value, making the first
		 MOVI.  */
	      md_number_to_chars (fragP->fr_opcode,
				  insn
				  | (((value >> 48) & ((1 << 16) - 1)) << 10),
				  4);

	      /* Add a SHORI with the midhigh bits.  Note that this insn lives
		 in the variable fragment part.  */
	      md_number_to_chars (fragP->fr_literal + old_fr_fix,
				  SHMEDIA_SHORI_OPC
				  | (reg << 4)
				  | (((value >> 32) & ((1 << 16) - 1)) << 10),
				  4);

	      /* Add a SHORI with the midlow bits.  */
	      md_number_to_chars (fragP->fr_literal + old_fr_fix + 4,
				  SHMEDIA_SHORI_OPC
				  | (reg << 4)
				  | (((value >> 16) & ((1 << 16) - 1)) << 10),
				  4);

	      /* Add a SHORI with the low bits.  */
	      md_number_to_chars (fragP->fr_literal + old_fr_fix + 8,
				  SHMEDIA_SHORI_OPC
				  | (reg << 4)
				  | ((value & ((1 << 16) - 1)) << 10), 4);
	      /* We took all of the variable part.  */
	      fragP->fr_fix += 12;
	    }

	  /* MOVI expansions that get here have not been converted to
	     PC-relative frags, but instead expanded by
	     md_number_to_chars or by calling shmedia_md_convert_frag
	     with final == FALSE.  We must not have them around as
	     frags anymore; symbols would be prematurely evaluated
	     when relaxing.  We will not need to have md_convert_frag
	     called again with them; any further handling is through
	     the already emitted fixups.  */
	  frag_wane (fragP);
	  break;
	}
      fragP->fr_var = md_relax_table[fragP->fr_subtype].rlx_length;
      break;

      /* For relaxation states that remain unchanged, report the
         estimated length.  */
    case C (SH64PCREL16_32, SH64PCREL16):
    case C (SH64PCREL16PT_32, SH64PCREL16):
    case C (SH64PCREL16_32, SH64PCREL32):
    case C (SH64PCREL16PT_32, SH64PCREL32):
    case C (SH64PCREL16_32, SH64PCRELPLT):
    case C (SH64PCREL16PT_32, SH64PCRELPLT):
    case C (SH64PCREL16_64, SH64PCREL16):
    case C (SH64PCREL16PT_64, SH64PCREL16):
    case C (SH64PCREL16_64, SH64PCREL32):
    case C (SH64PCREL16PT_64, SH64PCREL32):
    case C (SH64PCREL16_64, SH64PCREL48):
    case C (SH64PCREL16PT_64, SH64PCREL48):
    case C (SH64PCREL16_64, SH64PCREL64):
    case C (SH64PCREL16PT_64, SH64PCREL64):
    case C (SH64PCREL16_64, SH64PCRELPLT):
    case C (SH64PCREL16PT_64, SH64PCRELPLT):
    case C (MOVI_IMM_32, MOVI_16):
    case C (MOVI_IMM_32, MOVI_32):
    case C (MOVI_IMM_32, MOVI_GOTOFF):
    case C (MOVI_IMM_32_PCREL, MOVI_16):
    case C (MOVI_IMM_32_PCREL, MOVI_32):
    case C (MOVI_IMM_32_PCREL, MOVI_PLT):
    case C (MOVI_IMM_32_PCREL, MOVI_GOTPC):
    case C (MOVI_IMM_64, MOVI_16):
    case C (MOVI_IMM_64, MOVI_32):
    case C (MOVI_IMM_64, MOVI_48):
    case C (MOVI_IMM_64, MOVI_64):
    case C (MOVI_IMM_64, MOVI_GOTOFF):
    case C (MOVI_IMM_64_PCREL, MOVI_16):
    case C (MOVI_IMM_64_PCREL, MOVI_32):
    case C (MOVI_IMM_64_PCREL, MOVI_48):
    case C (MOVI_IMM_64_PCREL, MOVI_64):
    case C (MOVI_IMM_64_PCREL, MOVI_PLT):
    case C (MOVI_IMM_64_PCREL, MOVI_GOTPC):
      fragP->fr_var = md_relax_table[fragP->fr_subtype].rlx_length;
      break;

    default:
      abort ();
    }

  return fragP->fr_var + (fragP->fr_fix - old_fr_fix);
}

/* Parse an expression, SH64-style.  Copied from tc-sh.c, but with
   datatypes adjusted.  */

static char *
shmedia_parse_exp (char *s, shmedia_operand_info *op)
{
  char *save;
  char *new_pointer;

  save = input_line_pointer;
  input_line_pointer = s;
  expression (&op->immediate);
  if (op->immediate.X_op == O_absent)
    as_bad (_("missing operand"));
  new_pointer = input_line_pointer;
  input_line_pointer = save;
  return new_pointer;
}

/* Parse an operand.  Store pointer to next character in *PTR.  */

static void
shmedia_get_operand (char **ptr, shmedia_operand_info *op,
		     shmedia_arg_type argtype)
{
  char *src = *ptr;
  int mode = -1;
  unsigned int len;

  len = shmedia_parse_reg (src, &mode, &(op->reg), argtype);
  if (len)
    {
      *ptr = src + len;
      op->type = mode;
    }
  else
    {
      /* Not a reg, so it must be a displacement.  */
      *ptr = shmedia_parse_exp (src, op);
      op->type = A_IMMM;

      /* This is just an initialization; shmedia_get_operands will change
	 as needed.  */
      op->reloctype = BFD_RELOC_NONE;
    }
}

/* Parse the operands for this insn; return NULL if invalid, else return
   how much text was consumed.  */

static char *
shmedia_get_operands (shmedia_opcode_info *info, char *args,
		      shmedia_operands_info *operands)
{
  char *ptr = args;
  int i;

  if (*ptr == ' ')
    ptr++;

  for (i = 0; info->arg[i] != 0; i++)
    {
      memset (operands->operands + i, 0, sizeof (operands->operands[0]));

      /* No operand to get for these fields.  */
      if (info->arg[i] == A_REUSE_PREV)
	continue;

      shmedia_get_operand (&ptr, &operands->operands[i], info->arg[i]);

      /* Check operands type match.  */
      switch (info->arg[i])
	{
	case A_GREG_M:
	case A_GREG_N:
	case A_GREG_D:
	  if (operands->operands[i].type != A_GREG_M)
	    return NULL;
	  break;

	case A_FREG_G:
	case A_FREG_H:
	case A_FREG_F:
	  if (operands->operands[i].type != A_FREG_G)
	    return NULL;
	  break;

	case A_FVREG_G:
	case A_FVREG_H:
	case A_FVREG_F:
	  if (operands->operands[i].type != A_FVREG_G)
	    return NULL;
	  break;

	case A_FMREG_G:
	case A_FMREG_H:
	case A_FMREG_F:
	  if (operands->operands[i].type != A_FMREG_G)
	    return NULL;
	  break;

	case A_FPREG_G:
	case A_FPREG_H:
	case A_FPREG_F:
	  if (operands->operands[i].type != A_FPREG_G)
	    return NULL;
	  break;

	case A_DREG_G:
	case A_DREG_H:
	case A_DREG_F:
	  if (operands->operands[i].type != A_DREG_G)
	    return NULL;
	  break;

	case A_TREG_A:
	case A_TREG_B:
	  if (operands->operands[i].type != A_TREG_B)
	    return NULL;
	  break;

	case A_CREG_J:
	case A_CREG_K:
	  if (operands->operands[i].type != A_CREG_K)
	    return NULL;
	  break;

	case A_IMMS16:
	case A_IMMU16:
	  /* Check for an expression that looks like S & 65535 or
	     (S >> N) & 65535, where N = 0, 16, 32, 48.

	     Get the S and put at operands->operands[i].immediate, and
	     adjust operands->operands[i].reloctype.  */
	  {
	    expressionS *imm_expr = &operands->operands[i].immediate;
	    expressionS *right_expr;

	    if (operands->operands[i].type == A_IMMM
		&& imm_expr->X_op == O_bit_and
		&& imm_expr->X_op_symbol != NULL
		&& ((right_expr
		     = symbol_get_value_expression (imm_expr->X_op_symbol))
		    ->X_op == O_constant)
		&& right_expr->X_add_number == 0xffff)
	      {
		symbolS *inner = imm_expr->X_add_symbol;
		bfd_reloc_code_real_type reloctype = BFD_RELOC_SH_IMM_LOW16;
		expressionS *inner_expr
		  = symbol_get_value_expression (inner);

		if (inner_expr->X_op == O_right_shift)
		  {
		    expressionS *inner_right;

		    if (inner_expr->X_op_symbol != NULL
		      && ((inner_right
			   = symbol_get_value_expression (inner_expr
							  ->X_op_symbol))
			  ->X_op == O_constant))
		      {
			offsetT addnum
			  = inner_right->X_add_number;

			if (addnum == 0 || addnum == 16 || addnum == 32
			    || addnum == 48)
			  {
			    reloctype
			      = (addnum == 0
				 ? BFD_RELOC_SH_IMM_LOW16
				 : (addnum == 16
				    ? BFD_RELOC_SH_IMM_MEDLOW16
				    : (addnum == 32
				       ? BFD_RELOC_SH_IMM_MEDHI16
				       : BFD_RELOC_SH_IMM_HI16)));

			    inner = inner_expr->X_add_symbol;
			    inner_expr = symbol_get_value_expression (inner);
			  }
		      }
		  }

		/* I'm not sure I understand the logic, but evidently the
		   inner expression of a lone symbol is O_constant, with
		   the actual symbol in expr_section.  For a constant, the
		   section would be absolute_section.  For sym+offset,
		   it's O_symbol as always.  See expr.c:make_expr_symbol,
		   first statements.  */

		if (inner_expr->X_op == O_constant
		    && S_GET_SEGMENT (inner) != absolute_section)
		  {
		    operands->operands[i].immediate.X_op = O_symbol;
		    operands->operands[i].immediate.X_add_symbol = inner;
		    operands->operands[i].immediate.X_add_number = 0;
		  }
		else
		  operands->operands[i].immediate
		    = *symbol_get_value_expression (inner);

		operands->operands[i].reloctype = reloctype;
	      }
	  }
	  /* Fall through.  */
	case A_IMMS6:
	case A_IMMS6BY32:
	case A_IMMS10:
	case A_IMMS10BY1:
	case A_IMMS10BY2:
	case A_IMMS10BY4:
	case A_IMMS10BY8:
	case A_PCIMMS16BY4:
	case A_PCIMMS16BY4_PT:
	case A_IMMU5:
	case A_IMMU6:
	  if (operands->operands[i].type != A_IMMM)
	    return NULL;

	  if (sh_check_fixup (&operands->operands[i].immediate,
			      &operands->operands[i].reloctype))
	    {
	      as_bad (_("invalid PIC reference"));
	      return NULL;
	    }

	  break;

	default:
	  BAD_CASE (info->arg[i]);
	}

      if (*ptr == ',' && info->arg[i + 1])
	ptr++;
    }
  return ptr;
}


/* Find an opcode at the start of *STR_P in the hash table, and set
   *STR_P to the first character after the last one read.  */

static shmedia_opcode_info *
shmedia_find_cooked_opcode (char **str_p)
{
  char *str = *str_p;
  char *op_start;
  char *op_end;
  char name[20];
  unsigned int nlen = 0;

  /* Drop leading whitespace.  */
  while (*str == ' ')
    str++;

  /* Find the op code end.  */
  for (op_start = op_end = str;
       *op_end
       && nlen < sizeof (name) - 1
       && ! is_end_of_line[(unsigned char) *op_end]
       && ! ISSPACE ((unsigned char) *op_end);
       op_end++)
    {
      unsigned char c = op_start[nlen];

      /* The machine independent code will convert CMP/EQ into cmp/EQ
	 because it thinks the '/' is the end of the symbol.  Moreover,
	 all but the first sub-insn is a parallel processing insn won't
	 be capitalized.  Instead of hacking up the machine independent
	 code, we just deal with it here.  */
      c = TOLOWER (c);
      name[nlen] = c;
      nlen++;
    }

  name[nlen] = 0;
  *str_p = op_end;

  if (nlen == 0)
    as_bad (_("can't find opcode"));

  return
    (shmedia_opcode_info *) hash_find (shmedia_opcode_hash_control, name);
}

/* Build up an instruction, including allocating the frag.  */

static int
shmedia_build_Mytes (shmedia_opcode_info *opcode,
		     shmedia_operands_info *operands)
{
  unsigned long insn = opcode->opcode_base;
  int i, j;
  char *insn_loc = frag_more (4);

  /* The parameter to dwarf2_emit_insn is actually the offset to the start
     of the insn from the fix piece of instruction that was emitted.
     Since we want .debug_line addresses to record (address | 1) for
     SHmedia insns, we get the wanted effect by taking one off the size,
     knowing it's a multiple of 4.  We count from the first fix piece of
     the insn.  There must be no frags changes (frag_more or frag_var)
     calls in-between the frag_more call we account for, and this
     dwarf2_emit_insn call.  */
  dwarf2_emit_insn (3);

  /* This is stored into any frag_var operand.  */
  sh64_last_insn_frag = frag_now;

  /* Loop over opcode info, emit an instruction.  */
  for (i = 0, j = 0; opcode->arg[i]; i++)
    {
      shmedia_arg_type argtype = opcode->arg[i];
      shmedia_operand_info *opjp = &operands->operands[j];
      switch (argtype)
	{
	case A_TREG_A:
	case A_TREG_B:
	case A_GREG_M:
	case A_GREG_N:
	case A_GREG_D:
	case A_FREG_G:
	case A_FREG_H:
	case A_FREG_F:
	case A_FVREG_G:
	case A_FVREG_H:
	case A_FVREG_F:
	case A_FMREG_G:
	case A_FMREG_H:
	case A_FMREG_F:
	case A_FPREG_G:
	case A_FPREG_H:
	case A_FPREG_F:
	case A_DREG_G:
	case A_DREG_H:
	case A_DREG_F:
	case A_CREG_J:
	case A_CREG_K:
	  /* Six-bit register fields.  They just get filled with the
	     parsed register number.  */
	  insn |= (opjp->reg << opcode->nibbles[i]);
	  j++;
	  break;

	case A_REUSE_PREV:
	  /* Copy the register for the previous operand to this position.  */
	  insn |= (operands->operands[j - 1].reg << opcode->nibbles[i]);
	  j++;
	  break;

	case A_IMMS6:
	  insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					BFD_RELOC_SH_IMMS6);
	  j++;
	  break;

	case A_IMMS6BY32:
	  insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					BFD_RELOC_SH_IMMS6BY32);
	  j++;
	  break;

	case A_IMMS10BY1:
	case A_IMMS10:
	  insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					BFD_RELOC_SH_IMMS10);
	  j++;
	  break;

	case A_IMMS10BY2:
	  insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					BFD_RELOC_SH_IMMS10BY2);
	  j++;
	  break;

	case A_IMMS10BY4:
	  if (opjp->reloctype == BFD_RELOC_NONE)
	    insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					  BFD_RELOC_SH_IMMS10BY4);
	  else if (opjp->reloctype == BFD_RELOC_SH_GOTPLT32)
	    insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					  BFD_RELOC_SH_GOTPLT10BY4);
	  else if (opjp->reloctype == BFD_RELOC_32_GOT_PCREL)
	    insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					  BFD_RELOC_SH_GOT10BY4);
	  else
	    as_bad (_("invalid PIC reference"));
	  j++;
	  break;

	case A_IMMS10BY8:
	  if (opjp->reloctype == BFD_RELOC_NONE)
	    insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					  BFD_RELOC_SH_IMMS10BY8);
	  else if (opjp->reloctype == BFD_RELOC_SH_GOTPLT32)
	    insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					  BFD_RELOC_SH_GOTPLT10BY8);
	  else if (opjp->reloctype == BFD_RELOC_32_GOT_PCREL)
	    insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					  BFD_RELOC_SH_GOT10BY8);
	  else
	    as_bad (_("invalid PIC reference"));
	  j++;
	  break;

	case A_IMMS16:
	  /* Sneak a peek if this is the MOVI insn.  If so, check if we
	     should expand it.  */
	  if (opjp->reloctype == BFD_RELOC_32_GOT_PCREL)
	    opjp->reloctype = BFD_RELOC_SH_GOT_LOW16;
	  else if (opjp->reloctype == BFD_RELOC_SH_GOTPLT32)
	    opjp->reloctype = BFD_RELOC_SH_GOTPLT_LOW16;

	  if ((opjp->reloctype == BFD_RELOC_NONE
	       || opjp->reloctype == BFD_RELOC_32_GOTOFF
	       || opjp->reloctype == BFD_RELOC_32_PLT_PCREL
	       || opjp->reloctype == BFD_RELOC_SH_GOTPC)
	      && opcode->opcode_base == SHMEDIA_MOVI_OPC
	      && (opjp->immediate.X_op != O_constant
		  || opjp->immediate.X_add_number < -32768
		  || opjp->immediate.X_add_number > 32767)
	      && (sh64_expand
		  || opjp->reloctype == BFD_RELOC_32_GOTOFF
		  || opjp->reloctype == BFD_RELOC_32_PLT_PCREL
		  || opjp->reloctype == BFD_RELOC_SH_GOTPC))
	    {
	      int what = sh64_abi == sh64_abi_64 ? MOVI_IMM_64 : MOVI_IMM_32;
	      offsetT max = sh64_abi == sh64_abi_64 ? MOVI_64 : MOVI_32;
	      offsetT min = MOVI_16;
	      offsetT init = UNDEF_MOVI;
	      valueT addvalue
		= opjp->immediate.X_op_symbol != NULL
		? 0 : opjp->immediate.X_add_number;
	      symbolS *sym
		= opjp->immediate.X_op_symbol != NULL
		? make_expr_symbol (&opjp->immediate)
		: opjp->immediate.X_add_symbol;

	      if (opjp->reloctype == BFD_RELOC_32_GOTOFF)
		init = max = min = MOVI_GOTOFF;
	      else if (opjp->reloctype == BFD_RELOC_32_PLT_PCREL)
		{
		  init = max = min = MOVI_PLT;
		  what = (sh64_abi == sh64_abi_64
			  ? MOVI_IMM_64_PCREL
			  : MOVI_IMM_32_PCREL);
		}
	      else if (opjp->reloctype == BFD_RELOC_SH_GOTPC)
		{
		  init = max = min = MOVI_GOTPC;
		  what = (sh64_abi == sh64_abi_64
			  ? MOVI_IMM_64_PCREL
			  : MOVI_IMM_32_PCREL);
		}

	      frag_var (rs_machine_dependent,
			md_relax_table[C (what, max)].rlx_length,
			md_relax_table[C (what, min)].rlx_length,
			C (what, init), sym, addvalue, insn_loc);
	    }
	  else
	    insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					  (opjp->reloctype
					   == BFD_RELOC_NONE)
					  ? BFD_RELOC_SH_IMMS16
					  : opjp->reloctype);
	  j++;
	  break;

	case A_PCIMMS16BY4:
	  {
	    int what
	      = ((sh64_abi == sh64_abi_64 && ! sh64_pt32)
		 ? SH64PCREL16_64 : SH64PCREL16_32);
	    offsetT max
	      = ((sh64_abi == sh64_abi_64 && ! sh64_pt32)
		 ? SH64PCREL64 : SH64PCREL32);
	    offsetT min = SH64PCREL16;
	    offsetT init = UNDEF_SH64PCREL;

	    /* Don't allow complex expressions here.  */
	    if (opjp->immediate.X_op_symbol != NULL)
	      {
		as_bad (_("invalid operand: expression in PT target"));
		return 0;
	      }

	    if (opjp->reloctype == BFD_RELOC_32_PLT_PCREL)
	      init = max = min = SH64PCRELPLT;

	    /* If we're not expanding, then just emit a fixup.  */
	    if (sh64_expand || opjp->reloctype != BFD_RELOC_NONE)
	      frag_var (rs_machine_dependent,
			md_relax_table[C (what, max)].rlx_length,
			md_relax_table[C (what, min)].rlx_length,
			C (what, init),
			opjp->immediate.X_add_symbol,
			opjp->immediate.X_add_number,
			insn_loc);
	    else
	      insn |= shmedia_immediate_op (insn_loc, opjp, 1,
					    opjp->reloctype == BFD_RELOC_NONE
					    ? BFD_RELOC_SH_PT_16
					    : opjp->reloctype);

	    j++;
	    break;
	  }

	case A_PCIMMS16BY4_PT:
	  {
	    int what
	      = ((sh64_abi == sh64_abi_64 && ! sh64_pt32)
		 ? SH64PCREL16PT_64 : SH64PCREL16PT_32);
	    offsetT max
	      = ((sh64_abi == sh64_abi_64 && ! sh64_pt32)
		 ? SH64PCREL64 : SH64PCREL32);
	    offsetT min = SH64PCREL16;
	    offsetT init = UNDEF_SH64PCREL;

	    /* Don't allow complex expressions here.  */
	    if (opjp->immediate.X_op_symbol != NULL)
	      {
		as_bad (_("invalid operand: expression in PT target"));
		return 0;
	      }

	    if (opjp->reloctype == BFD_RELOC_32_PLT_PCREL)
	      init = max = min = SH64PCRELPLT;

	    /* If we're not expanding, then just emit a fixup.  */
	    if (sh64_expand || opjp->reloctype != BFD_RELOC_NONE)
	      frag_var (rs_machine_dependent,
			md_relax_table[C (what, max)].rlx_length,
			md_relax_table[C (what, min)].rlx_length,
			C (what, init),
			opjp->immediate.X_add_symbol,
			opjp->immediate.X_add_number,
			insn_loc);
	    else
	      /* This reloc-type is just temporary, so we can distinguish
		 PTA from PT.  It is changed in shmedia_md_apply_fix to
		 BFD_RELOC_SH_PT_16.  */
	      insn |= shmedia_immediate_op (insn_loc, opjp, 1,
					    opjp->reloctype == BFD_RELOC_NONE
					    ? SHMEDIA_BFD_RELOC_PT
					    : opjp->reloctype);

	    j++;
	    break;
	  }

	case A_IMMU5:
	  insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					BFD_RELOC_SH_IMMU5);
	  j++;
	  break;

	case A_IMMU6:
	  insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					BFD_RELOC_SH_IMMU6);
	  j++;
	  break;

	case A_IMMU16:
	  insn |= shmedia_immediate_op (insn_loc, opjp, 0,
					(opjp->reloctype
					 == BFD_RELOC_NONE)
					? BFD_RELOC_SH_IMMU16
					: opjp->reloctype);
	  j++;
	  break;

	default:
	  BAD_CASE (argtype);
	}
    }

  md_number_to_chars (insn_loc, insn, 4);
  return 4;
}

/* Assemble a SHmedia instruction.  */

static void
shmedia_md_assemble (char *str)
{
  char *op_end;
  shmedia_opcode_info *opcode;
  shmedia_operands_info operands;
  int size;

  opcode = shmedia_find_cooked_opcode (&str);
  op_end = str;

  if (opcode == NULL)
    {
      as_bad (_("unknown opcode"));
      return;
    }

  /* Start a SHmedia code region, if there has been pseudoinsns or similar
     seen since the last one.  */
  if (!seen_insn)
    {
      sh64_update_contents_mark (TRUE);
      sh64_set_contents_type (CRT_SH5_ISA32);
      seen_insn = TRUE;
    }

  op_end = shmedia_get_operands (opcode, op_end, &operands);

  if (op_end == NULL)
    {
      as_bad (_("invalid operands to %s"), opcode->name);
      return;
    }

  if (*op_end)
    {
      as_bad (_("excess operands to %s"), opcode->name);
      return;
    }

  size = shmedia_build_Mytes (opcode, &operands);
  if (size == 0)
    return;
}

/* Hook called from md_begin in tc-sh.c.  */

void
shmedia_md_begin (void)
{
  const shmedia_opcode_info *shmedia_opcode;
  shmedia_opcode_hash_control = hash_new ();

  /* Create opcode table for SHmedia mnemonics.  */
  for (shmedia_opcode = shmedia_table;
       shmedia_opcode->name;
       shmedia_opcode++)
    hash_insert (shmedia_opcode_hash_control, shmedia_opcode->name,
		 (char *) shmedia_opcode);
}

/* Switch instruction set.  Only valid if one of the --isa or --abi
   options was specified.  */

static void
s_sh64_mode (int ignore ATTRIBUTE_UNUSED)
{
  char *name = input_line_pointer, ch;

  /* Make sure data up to this location is handled according to the
     previous ISA.  */
  sh64_update_contents_mark (TRUE);

  while (!is_end_of_line[(unsigned char) *input_line_pointer])
    input_line_pointer++;
  ch = *input_line_pointer;
  *input_line_pointer = '\0';

  /* If the mode was not set before, explicitly or implicitly, then we're
     not emitting SH64 code, so this pseudo is invalid.  */
  if (sh64_isa_mode == sh64_isa_unspecified)
    as_bad (_("The `.mode %s' directive is not valid with this architecture"),
	    name);

  if (strcasecmp (name, "shcompact") == 0)
    sh64_isa_mode = sh64_isa_shcompact;
  else if (strcasecmp (name, "shmedia") == 0)
    sh64_isa_mode = sh64_isa_shmedia;
  else
    as_bad (_("Invalid argument to .mode: %s"), name);

  /* Make a new frag, marking it with the supposedly-changed ISA.  */
  frag_wane (frag_now);
  frag_new (0);

  /* Contents type up to this new point is the same as before; don't add a
     data region just because the new frag we created.  */
  sh64_update_contents_mark (FALSE);

  *input_line_pointer = ch;
  demand_empty_rest_of_line ();
}

/* Check that the right ABI is used.  Only valid if one of the --isa or
   --abi options was specified.  */

static void
s_sh64_abi (int ignore ATTRIBUTE_UNUSED)
{
  char *name = input_line_pointer, ch;

  while (!is_end_of_line[(unsigned char) *input_line_pointer])
    input_line_pointer++;
  ch = *input_line_pointer;
  *input_line_pointer = '\0';

  /* If the mode was not set before, explicitly or implicitly, then we're
     not emitting SH64 code, so this pseudo is invalid.  */
  if (sh64_abi == sh64_abi_unspecified)
    as_bad (_("The `.abi %s' directive is not valid with this architecture"),
	    name);

  if (strcmp (name, "64") == 0)
    {
      if (sh64_abi != sh64_abi_64)
	as_bad (_("`.abi 64' but command-line options do not specify 64-bit ABI"));
    }
  else if (strcmp (name, "32") == 0)
    {
      if (sh64_abi != sh64_abi_32)
	as_bad (_("`.abi 32' but command-line options do not specify 32-bit ABI"));
    }
  else
    as_bad (_("Invalid argument to .abi: %s"), name);

  *input_line_pointer = ch;
  demand_empty_rest_of_line ();
}

/* This function is the first target-specific function called after
   parsing command-line options.  Therefore we set default values from
   command-line options here and do some sanity checking we couldn't do
   when options were being parsed.  */

const char *
sh64_target_format (void)
{
#ifdef TE_NetBSD
  /* For NetBSD, if the ISA is unspecified, always use SHmedia.  */
  if (preset_target_arch == 0 && sh64_isa_mode == sh64_isa_unspecified)
    sh64_isa_mode = sh64_isa_shmedia;

  /* If the ABI is unspecified, select a default: based on how
     we were configured: sh64 == sh64_abi_64, else sh64_abi_32.  */
  if (sh64_abi == sh64_abi_unspecified)
    {
      if (preset_target_arch != 0 || sh64_isa_mode == sh64_isa_shcompact)
	sh64_abi = sh64_abi_32;
      else if (strncmp (TARGET_CPU, "sh64", 4) == 0)
        sh64_abi = sh64_abi_64;
      else
        sh64_abi = sh64_abi_32;
    }
#endif

#ifdef TE_LINUX
  if (preset_target_arch == 0 && sh64_isa_mode == sh64_isa_unspecified)
    sh64_isa_mode = sh64_isa_shmedia;

  if (sh64_abi == sh64_abi_unspecified)
    sh64_abi = sh64_abi_32;
#endif

  if (sh64_abi == sh64_abi_64 && sh64_isa_mode == sh64_isa_unspecified)
    sh64_isa_mode = sh64_isa_shmedia;

  if (sh64_abi == sh64_abi_32 && sh64_isa_mode == sh64_isa_unspecified)
    sh64_isa_mode = sh64_isa_shcompact;

  if (sh64_isa_mode == sh64_isa_shcompact
      && sh64_abi == sh64_abi_unspecified)
    sh64_abi = sh64_abi_32;

  if (sh64_isa_mode == sh64_isa_shmedia
      && sh64_abi == sh64_abi_unspecified)
    sh64_abi = sh64_abi_64;

  if (sh64_isa_mode == sh64_isa_unspecified && ! sh64_mix)
    as_bad (_("-no-mix is invalid without specifying SHcompact or SHmedia"));

  if ((sh64_isa_mode == sh64_isa_unspecified
       || sh64_isa_mode == sh64_isa_shmedia)
      && sh64_shcompact_const_crange)
    as_bad (_("-shcompact-const-crange is invalid without SHcompact"));

  if (sh64_pt32 && sh64_abi != sh64_abi_64)
    as_bad (_("-expand-pt32 only valid with -abi=64"));

  if (! sh64_expand && sh64_isa_mode == sh64_isa_unspecified)
    as_bad (_("-no-expand only valid with SHcompact or SHmedia"));

  if (sh64_pt32 && ! sh64_expand)
    as_bad (_("-expand-pt32 invalid together with -no-expand"));

#ifdef TE_NetBSD
  if (sh64_abi == sh64_abi_64)
    return (target_big_endian ? "elf64-sh64-nbsd" : "elf64-sh64l-nbsd");
  else
    return (target_big_endian ? "elf32-sh64-nbsd" : "elf32-sh64l-nbsd");
#elif defined (TE_LINUX)
  if (sh64_abi == sh64_abi_64)
    return (target_big_endian ? "elf64-sh64big-linux" : "elf64-sh64-linux");
  else
    return (target_big_endian ? "elf32-sh64big-linux" : "elf32-sh64-linux");
#else
  /* When the ISA is not one of SHmedia or SHcompact, use the old SH
     object format.  */
  if (sh64_isa_mode == sh64_isa_unspecified)
    return (target_big_endian ? "elf32-sh" : "elf32-shl");
  else if (sh64_abi == sh64_abi_64)
    return (target_big_endian ? "elf64-sh64" : "elf64-sh64l");
  else
    return (target_big_endian ? "elf32-sh64" : "elf32-sh64l");
#endif
}

/* The worker function of TARGET_MACH.  */

int
sh64_target_mach (void)
{
  /* We need to explicitly set bfd_mach_sh5 instead of the default 0.  But
     we only do this for the 64-bit ABI: if we do it for the 32-bit ABI,
     the SH5 info in the bfd_arch_info structure will be selected.
     However correct, as the machine has 64-bit addresses, functions
     expected to emit 32-bit data for addresses will start failing.  For
     example, the dwarf2dbg.c functions will emit 64-bit debugging format,
     and we don't want that in the 32-bit ABI.

     We could have two bfd_arch_info structures for SH64; one for the
     32-bit ABI and one for the rest (64-bit ABI).  But that would be a
     bigger kludge: it's a flaw in the BFD design, and we need to just
     work around it by having the default machine set here in the
     assembler.  For everything else but the assembler, the various bfd
     functions will set the machine type right to bfd_mach_sh5 from object
     file header flags regardless of the 0 here.  */

  return (sh64_abi == sh64_abi_64) ? bfd_mach_sh5 : 0;
}

/* This is MD_PCREL_FROM_SECTION, we we define so it is called instead of
   md_pcrel_from (in tc-sh.c).  */

valueT
shmedia_md_pcrel_from_section (struct fix *fixP, segT sec ATTRIBUTE_UNUSED)
{
  /* Use the ISA for the instruction to decide which offset to use.  We
     can glean it from the fisup type.  */
  switch (fixP->fx_r_type)
    {
    case BFD_RELOC_SH_IMM_LOW16:
    case BFD_RELOC_SH_IMM_MEDLOW16:
    case BFD_RELOC_SH_IMM_MEDHI16:
    case BFD_RELOC_SH_IMM_HI16:
    case BFD_RELOC_SH_IMM_LOW16_PCREL:
    case BFD_RELOC_SH_IMM_MEDLOW16_PCREL:
    case BFD_RELOC_SH_IMM_MEDHI16_PCREL:
    case BFD_RELOC_SH_IMM_HI16_PCREL:
    case BFD_RELOC_SH_IMMU5:
    case BFD_RELOC_SH_IMMU6:
    case BFD_RELOC_SH_IMMS6:
    case BFD_RELOC_SH_IMMS10:
    case BFD_RELOC_SH_IMMS10BY2:
    case BFD_RELOC_SH_IMMS10BY4:
    case BFD_RELOC_SH_IMMS10BY8:
    case BFD_RELOC_SH_IMMS16:
    case BFD_RELOC_SH_IMMU16:
    case BFD_RELOC_SH_PT_16:
    case SHMEDIA_BFD_RELOC_PT:
      /* PC-relative relocs are relative to the address of the last generated
	 instruction, i.e. fx_size - 4.  */
      return SHMEDIA_MD_PCREL_FROM_FIX (fixP);

    case BFD_RELOC_64:
    case BFD_RELOC_64_PCREL:
      /* Fall through.  */

    default:
      /* If section was SHcompact, use its function.  */
      return (valueT) md_pcrel_from_section (fixP, sec);
    }

  know (0 /* Shouldn't get here.  */);
  return 0;
}

/* Create one .cranges descriptor from two symbols, STARTSYM marking begin
   and ENDSYM marking end, and CR_TYPE specifying the type.  */

static void
sh64_emit_crange (symbolS *startsym, symbolS *endsym,
		  enum sh64_elf_cr_type cr_type)
{
  expressionS exp;
  segT current_seg = now_seg;
  subsegT current_subseg = now_subseg;

  asection *cranges
    = bfd_make_section_old_way (stdoutput,
				SH64_CRANGES_SECTION_NAME);

  /* Temporarily change to the .cranges section.  */
  subseg_set (cranges, 0);

  /* Emit the cr_addr part.  */
  exp.X_op = O_symbol;
  exp.X_add_number = 0;
  exp.X_op_symbol = NULL;
  exp.X_add_symbol = startsym;
  emit_expr (&exp, 4);

  /* Emit the cr_size part.  */
  exp.X_op = O_subtract;
  exp.X_add_number = 0;
  exp.X_add_symbol = endsym;
  exp.X_op_symbol = startsym;
  emit_expr (&exp, 4);

  /* Emit the cr_size part.  */
  exp.X_op = O_constant;
  exp.X_add_number = cr_type;
  exp.X_add_symbol = NULL;
  exp.X_op_symbol = NULL;
  emit_expr (&exp, 2);

  /* Now back to our regular program.  */
  subseg_set (current_seg, current_subseg);
}

/* Called when the assembler is about to emit contents of some type into
   SEG, so it is *known* that the type of that new contents is in
   NEW_CONTENTS_TYPE.  If just switching back and forth between different
   contents types (for example, with consecutive .mode pseudos), then this
   function isn't called.  */

static void
sh64_set_contents_type (enum sh64_elf_cr_type new_contents_type)
{
  segment_info_type *seginfo;

  /* We will not be called when emitting .cranges output, since callers
     stop that.  Validize that assumption.  */
  know (!emitting_crange);

  seginfo = seg_info (now_seg);

  if (seginfo)
    {
      symbolS *symp = seginfo->tc_segment_info_data.last_contents_mark;

      enum sh64_elf_cr_type contents_type
	= seginfo->tc_segment_info_data.contents_type;

      /* If it was just SHcompact switching between code and constant
	 pool, don't change contents type.  Just make sure we don't set
	 the contents type to data, as that would join with a data-region
	 in SHmedia mode.  */
      if (sh64_isa_mode == sh64_isa_shcompact
	  && ! sh64_shcompact_const_crange)
	new_contents_type = CRT_SH5_ISA16;

      /* If nothing changed, stop here.  */
      if (contents_type == new_contents_type)
	return;

      /* If we're in 64-bit ABI mode, we do not emit .cranges, as it is
	 only specified for 32-bit addresses.  It could presumably be
	 extended, but in 64-bit ABI mode we don't have SHcompact code, so
	 we would only use it to mark code and data.  */
      if (sh64_abi == sh64_abi_64)
	{
	  /* Make the code type "sticky".  We don't want to set the
	     sections contents type to data if there's any code in it as
	     we don't have .cranges in 64-bit mode to notice the
	     difference.  */
	  seginfo->tc_segment_info_data.contents_type
	    = (new_contents_type == CRT_SH5_ISA32
	       || contents_type == CRT_SH5_ISA32)
	    ? CRT_SH5_ISA32 : new_contents_type;
	  return;
	}

      /* If none was marked, create a start symbol for this range and
	 perhaps as a closing symbol for the old one.  */
      if (symp == NULL)
	symp = symbol_new (FAKE_LABEL_NAME, now_seg, (valueT) frag_now_fix (),
			   frag_now);

      /* We will use this symbol, so don't leave a pointer behind.  */
      seginfo->tc_segment_info_data.last_contents_mark = NULL;

      /* We'll be making only datalabel references to it, if we emit a
	 .cranges descriptor, so remove any code flag.  */
      S_SET_OTHER (symp, S_GET_OTHER (symp) & ~STO_SH5_ISA32);

      /* If we have already marked the start of a range, we need to close
	 and emit it before marking a new one, so emit a new .cranges
	 descriptor into the .cranges section.  */
      if (seginfo->tc_segment_info_data.mode_start_symbol)
	{
	  /* If we're not supposed to emit mixed-mode sections, make it an
	     error, but continue processing.  */
	  if (! sh64_mix
	      && (new_contents_type == CRT_SH5_ISA32
		  || contents_type == CRT_SH5_ISA32))
	    as_bad (
_("SHmedia code not allowed in same section as constants and SHcompact code"));

	  emitting_crange = TRUE;
	  sh64_emit_crange (seginfo->tc_segment_info_data.mode_start_symbol,
			    symp, contents_type);
	  emitting_crange = FALSE;
	  seginfo->tc_segment_info_data.emitted_ranges++;
	}

      seginfo->tc_segment_info_data.mode_start_symbol = symp;
      seginfo->tc_segment_info_data.mode_start_subseg = now_subseg;
      seginfo->tc_segment_info_data.contents_type = new_contents_type;

      /* Always reset this, so the SHcompact code will emit a reloc when
	 it prepares to relax.  */
      seginfo->tc_segment_info_data.in_code = 0;
    }
  else
    as_bad (_("No segment info for current section"));
}

/* Hook when defining symbols and labels.  We set the ST_OTHER field if
   the symbol is "shmedia" (with "bitor 1" automatically applied).  Simple
   semantics for a label being "shmedia" : It was defined when .mode
   SHmedia was in effect, and it was defined in a code section.  It
   doesn't matter whether or not an assembled opcode is nearby.  */

void
sh64_frob_label (symbolS *symp)
{
  segT seg = S_GET_SEGMENT (symp);
  static const symbolS *null = NULL;

  /* Reset the tc marker for all newly created symbols.  */
  symbol_set_tc (symp, (symbolS **) &null);

  if (seg != NULL && sh64_isa_mode == sh64_isa_shmedia && subseg_text_p (seg))
    S_SET_OTHER (symp, S_GET_OTHER (symp) | STO_SH5_ISA32);
}

/* Handle the "datalabel" qualifier.  We need to call "operand", but it's
   static, so a function pointer is passed here instead.  FIXME: A target
   hook for qualifiers is needed; we currently use the md_parse_name
   symbol hook.  */

int
sh64_consume_datalabel (const char *name, expressionS *exp,
			enum expr_mode mode, char *cp,
			segT (*operandf) (expressionS *, enum expr_mode))
{
  static int parsing_datalabel = 0;

  if (strcasecmp (name, "datalabel") == 0)
    {
      int save_parsing_datalabel = parsing_datalabel;

      if (parsing_datalabel)
	as_bad (_("duplicate datalabel operator ignored"));

      *input_line_pointer = *cp;
      parsing_datalabel = 1;
      (*operandf) (exp, expr_normal);
      parsing_datalabel = save_parsing_datalabel;

      if (exp->X_op == O_symbol || exp->X_op == O_PIC_reloc)
	{
	  symbolS *symp = exp->X_add_symbol;
	  segT symseg = S_GET_SEGMENT (symp);

	  /* If the symbol is defined to something that is already a
	     datalabel, we don't need to bother with any special handling.  */
	  if (symseg != undefined_section
	      && S_GET_OTHER (symp) != STO_SH5_ISA32)
	    /* Do nothing.  */
	    ;
	  else
	    {
	      symbolS *dl_symp;
	      const char * sname = S_GET_NAME (symp);
	      char *dl_name
		= xmalloc (strlen (sname) + sizeof (DATALABEL_SUFFIX));

	      /* Now we copy the datalabel-qualified symbol into a symbol
		 with the same name, but with " DL" appended.  We mark the
		 symbol using the TC_SYMFIELD_TYPE field with a pointer to
		 the main symbol, so we don't have to inspect all symbol
		 names.  Note that use of "datalabel" is not expected to
		 be a common case.  */
	      strcpy (dl_name, sname);
	      strcat (dl_name, DATALABEL_SUFFIX);

	      /* A FAKE_LABEL_NAME marks "$" or ".".  There can be any
		 number of them and all have the same (faked) name; we
		 must make a new one each time.  */
	      if (strcmp (sname, FAKE_LABEL_NAME) == 0)
		dl_symp = symbol_make (dl_name);
	      else
		dl_symp = symbol_find_or_make (dl_name);

	      free (dl_name);
	      symbol_set_value_expression (dl_symp,
					   symbol_get_value_expression (symp));
	      S_SET_SEGMENT (dl_symp, symseg);
	      symbol_set_frag (dl_symp, symbol_get_frag (symp));
	      symbol_set_tc (dl_symp, &symp);
	      copy_symbol_attributes (dl_symp, symp);
	      exp->X_add_symbol = dl_symp;

	      /* Unset the BranchTarget mark that can be set at symbol
		 creation or attributes copying.  */
	      S_SET_OTHER (dl_symp, S_GET_OTHER (dl_symp) & ~STO_SH5_ISA32);

	      /* The GLOBAL and WEAK attributes are not copied over by
		 copy_symbol_attributes.  Do it here.  */
	      if (S_IS_WEAK (symp))
		S_SET_WEAK (dl_symp);
	      else if (S_IS_EXTERNAL (symp))
		S_SET_EXTERNAL (dl_symp);
	    }
	}
      /* Complain about other types of operands than symbol, unless they
	 have already been complained about.  A constant is always a
	 datalabel.  Removing the low bit would therefore be wrong.
	 Complaining about it would also be wrong.  */
      else if (exp->X_op != O_illegal
	       && exp->X_op != O_absent
	       && exp->X_op != O_constant)
	as_bad (_("Invalid DataLabel expression"));

      *cp = *input_line_pointer;

      return 1;
    }

  return sh_parse_name (name, exp, mode, cp);
}

/* This function is called just before symbols are being output.  It
   returns zero when a symbol must be output, non-zero otherwise.
   Datalabel references that were fully resolved to local symbols are not
   necessary to output.  We also do not want to output undefined symbols
   that are not used in relocs.  For symbols that are used in a reloc, it
   does not matter what we set here.  If it is *not* used in a reloc, then
   it was probably the datalabel counterpart that was used in a reloc;
   then we need not output the main symbol.  */

int
sh64_exclude_symbol (symbolS *symp)
{
  symbolS *main_symbol = *symbol_get_tc (symp);

  return main_symbol != NULL || ! S_IS_DEFINED (symp);
}

/* If we haven't seen an insn since the last update, and location
   indicators have moved (a new frag, new location within frag) we have
   emitted data, so change contents type to data.  Forget that we have
   seen a sequence of insns and store the current location so we can mark
   a new region if needed.  */

static void
sh64_update_contents_mark (bfd_boolean update_type)
{
  segment_info_type *seginfo;
  seginfo = seg_info (now_seg);

  if (seginfo != NULL)
    {
      symbolS *symp = seginfo->tc_segment_info_data.last_contents_mark;

      if (symp == NULL)
	{
	  symp = symbol_new (FAKE_LABEL_NAME, now_seg,
			     (valueT) frag_now_fix (), frag_now);
	  seginfo->tc_segment_info_data.last_contents_mark = symp;
	}
      else
	{
	  /* If we have moved location since last flush, we need to emit a
	     data range.  The previous contents type ended at the location
	     of the last update.  */
	  if ((S_GET_VALUE (symp) != frag_now_fix ()
	       || symbol_get_frag (symp) != frag_now))
	    {
	      enum sh64_elf_cr_type contents_type
		= seginfo->tc_segment_info_data.contents_type;

	      if (update_type
		  && contents_type != CRT_DATA
		  && contents_type != CRT_NONE
		  && ! seen_insn)
		{
		  sh64_set_contents_type (CRT_DATA);
		  symp = seginfo->tc_segment_info_data.last_contents_mark;
		}

	      /* If the symbol wasn't used up to make up a new range
		 descriptor, update it to this new location.  */
	      if (symp)
		{
		  S_SET_VALUE (symp, (valueT) frag_now_fix ());
		  symbol_set_frag (symp, frag_now);
		}
	    }
	}
    }

  seen_insn = FALSE;
}

/* Called when the assembler is about to output some data, or maybe it's
   just switching segments.  */

void
sh64_flush_pending_output (void)
{
  sh64_update_contents_mark (TRUE);
  sh_flush_pending_output ();
}

/* Flush out the last crange descriptor after all insns have been emitted.  */

static void
sh64_flush_last_crange (bfd *abfd ATTRIBUTE_UNUSED, asection *seg,
			void *countparg ATTRIBUTE_UNUSED)
{
  segment_info_type *seginfo;

  seginfo = seg_info (seg);

  if (seginfo
      /* Only emit .cranges descriptors if we would make it more than one.  */
      && seginfo->tc_segment_info_data.emitted_ranges != 0)
    {
      symbolS *symp;

      /* We need a closing symbol, so switch to the indicated section and
	 emit it.  */

      /* Change to the section we're about to handle.  */
      subseg_set (seg, seginfo->tc_segment_info_data.mode_start_subseg);

      symp = symbol_new (FAKE_LABEL_NAME, now_seg, (valueT) frag_now_fix (),
			 frag_now);

      /* We'll be making a datalabel reference to it, so remove any code
         flag.  */
      S_SET_OTHER (symp, S_GET_OTHER (symp) & ~STO_SH5_ISA32);

      sh64_emit_crange (seginfo->tc_segment_info_data.mode_start_symbol,
			symp,
			seginfo->tc_segment_info_data.contents_type);
    }
}

/* If and only if we see a call to md_number_to_chars without flagging the
   start of an insn, we set the contents type to CRT_DATA, and only when
   in SHmedia mode.  Note that by default we don't bother changing when
   going from SHcompact to data, as the constant pools in GCC-generated
   SHcompact code would create an inordinate amount of .cranges
   descriptors.  */

static void
sh64_flag_output (void)
{
  if (sh64_isa_mode != sh64_isa_unspecified
      && !seen_insn
      && !sh64_end_of_assembly
      && !emitting_crange)
    {
      md_flush_pending_output ();
      sh64_set_contents_type (CRT_DATA);
    }
}

/* Vtables don't need "datalabel" but we allow it by simply deleting
   any we find.  */

static char *
strip_datalabels (void)
{
  char *src, *dest, *start=input_line_pointer;

  for (src=input_line_pointer, dest=input_line_pointer; *src != '\n'; )
    {
      if (strncasecmp (src, "datalabel", 9) == 0
	  && ISSPACE (src[9])
	  && (src == start || !(ISALNUM (src[-1])) || src[-1] == '_'))
	src += 10;
      else
	*dest++ = *src++;
    }

  if (dest < src)
    *dest = '\n';
  return src + 1;
}

static void
sh64_vtable_entry (int ignore ATTRIBUTE_UNUSED)
{
  char *eol = strip_datalabels ();

  obj_elf_vtable_entry (0);
  input_line_pointer = eol;
}

static void
sh64_vtable_inherit (int ignore ATTRIBUTE_UNUSED)
{
  char *eol = strip_datalabels ();

  obj_elf_vtable_inherit (0);
  input_line_pointer = eol;
}

int
sh64_fake_label (const char *name)
{
  size_t len;

  if (strcmp (name, FAKE_LABEL_NAME) == 0)
    return 1;

  len = strlen (name);
  if (len >= (sizeof (DATALABEL_SUFFIX) - 1))
    return strcmp (&name [len - sizeof (DATALABEL_SUFFIX) + 1],
		   DATALABEL_SUFFIX) == 0;

  return 0;
}
