/* tc-sh64.c -- Assemble code for the SuperH SH SHcompact and SHmedia.
   Copyright 2000, 2001, 2002, 2003, 2004, 2005, 2006
   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 2, 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 an 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;

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

/* 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)
{
  know (fixP->fx_frag->fr_type == rs_machine_dependent);

  /* 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:
      know (0 /* Shouldn't get here.  */);
      break;

    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 *name = S_GET_NAME (symp);
	      char *dl_name
		= xmalloc (strlen (name) + 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, name);
	      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 (name, 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;
}
