/* tc-cr16.c -- Assembler code for the CR16 CPU core.
   Copyright (C) 2007-2021 Free Software Foundation, Inc.

   Contributed by M R Swami Reddy <MR.Swami.Reddy@nsc.com>

   This file is part of GAS, the GNU Assembler.

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

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

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

#include "as.h"
#include "safe-ctype.h"
#include "dwarf2dbg.h"
#include "opcode/cr16.h"
#include "elf/cr16.h"

#include <limits.h>
#ifndef CHAR_BIT
#define CHAR_BIT 8
#endif

/* Word is considered here as a 16-bit unsigned short int.  */
#define WORD_SHIFT  16

/* Register is 2-byte size.  */
#define REG_SIZE   2

/* Maximum size of a single instruction (in words).  */
#define INSN_MAX_SIZE   3

/* Maximum bits which may be set in a `mask16' operand.  */
#define MAX_REGS_IN_MASK16  8

/* Assign a number NUM, shifted by SHIFT bytes, into a location
   pointed by index BYTE of array 'output_opcode'.  */
#define CR16_PRINT(BYTE, NUM, SHIFT)   output_opcode[BYTE] |= (NUM) << (SHIFT)

/* Operand errors.  */
typedef enum
  {
    OP_LEGAL = 0,       /* Legal operand.  */
    OP_OUT_OF_RANGE,    /* Operand not within permitted range.  */
    OP_NOT_EVEN         /* Operand is Odd number, should be even.  */
  }
op_err;

/* Opcode mnemonics hash table.  */
static htab_t cr16_inst_hash;
/* CR16 registers hash table.  */
static htab_t reg_hash;
/* CR16 register pair hash table.  */
static htab_t regp_hash;
/* CR16 processor registers hash table.  */
static htab_t preg_hash;
/* CR16 processor registers 32 bit hash table.  */
static htab_t pregp_hash;
/* Current instruction we're assembling.  */
const inst *instruction;


static int code_label = 0;

/* Global variables.  */

/* Array to hold an instruction encoding.  */
long output_opcode[2];

/* Nonzero means a relocatable symbol.  */
int relocatable;

/* A copy of the original instruction (used in error messages).  */
char ins_parse[MAX_INST_LEN];

/* The current processed argument number.  */
int cur_arg_num;

/* Generic assembler global variables which must be defined by all targets.  */

/* Characters which always start a comment.  */
const char comment_chars[] = "#";

/* Characters which start a comment at the beginning of a line.  */
const char line_comment_chars[] = "#";

/* This array holds machine specific line separator characters.  */
const char line_separator_chars[] = ";";

/* Chars that can be used to separate mant from exp in floating point nums.  */
const char EXP_CHARS[] = "eE";

/* Chars that mean this number is a floating point constant as in 0f12.456  */
const char FLT_CHARS[] = "f'";

#ifdef OBJ_ELF
/* Pre-defined "_GLOBAL_OFFSET_TABLE_"  */
symbolS * GOT_symbol;
#endif

/* Target-specific multicharacter options, not const-declared at usage.  */
const char *md_shortopts = "";
struct option md_longopts[] =
{
  {NULL, no_argument, NULL, 0}
};
size_t md_longopts_size = sizeof (md_longopts);

static void
l_cons (int nbytes)
{
  int c;
  expressionS exp;

#ifdef md_flush_pending_output
  md_flush_pending_output ();
#endif

  if (is_it_end_of_statement ())
    {
      demand_empty_rest_of_line ();
      return;
    }

#ifdef TC_ADDRESS_BYTES
  if (nbytes == 0)
    nbytes = TC_ADDRESS_BYTES ();
#endif

#ifdef md_cons_align
  md_cons_align (nbytes);
#endif

  c = 0;
  do
    {
      unsigned int bits_available = BITS_PER_CHAR * nbytes;
      char *hold = input_line_pointer;

      expression (&exp);

      if (*input_line_pointer == ':')
	{
	  /* Bitfields.  */
	  long value = 0;

	  for (;;)
	    {
	      unsigned long width;

	      if (*input_line_pointer != ':')
		{
		  input_line_pointer = hold;
		  break;
		}
	      if (exp.X_op == O_absent)
		{
		  as_warn (_("using a bit field width of zero"));
		  exp.X_add_number = 0;
		  exp.X_op = O_constant;
		}

	      if (exp.X_op != O_constant)
		{
		  *input_line_pointer = '\0';
		  as_bad (_("field width \"%s\" too complex for a bitfield"),
			  hold);
		  *input_line_pointer = ':';
		  demand_empty_rest_of_line ();
		  return;
		}

	      if ((width = exp.X_add_number) >
		  (unsigned int)(BITS_PER_CHAR * nbytes))
		{
		  as_warn (ngettext ("field width %lu too big to fit in %d"
				     " byte: truncated to %d bits",
				     "field width %lu too big to fit in %d"
				     " bytes: truncated to %d bits",
				     nbytes),
			   width, nbytes, (BITS_PER_CHAR * nbytes));
		  width = BITS_PER_CHAR * nbytes;
		}

	      if (width > bits_available)
		{
		  /* FIXME-SOMEDAY: backing up and reparsing is wasteful.  */
		  input_line_pointer = hold;
		  exp.X_add_number = value;
		  break;
		}

	      /* Skip ':'.  */
	      hold = ++input_line_pointer;

	      expression (&exp);
	      if (exp.X_op != O_constant)
		{
		  char cache = *input_line_pointer;

		  *input_line_pointer = '\0';
		  as_bad (_("field value \"%s\" too complex for a bitfield"),
			  hold);
		  *input_line_pointer = cache;
		  demand_empty_rest_of_line ();
		  return;
		}

	      value |= ((~(-(1 << width)) & exp.X_add_number)
			<< ((BITS_PER_CHAR * nbytes) - bits_available));

	      if ((bits_available -= width) == 0
		  || is_it_end_of_statement ()
		  || *input_line_pointer != ',')
		break;

	      hold = ++input_line_pointer;
	      expression (&exp);
	    }

	  exp.X_add_number = value;
	  exp.X_op = O_constant;
	  exp.X_unsigned = 1;
	}

      if ((*(input_line_pointer) == '@') && (*(input_line_pointer +1) == 'c'))
	code_label = 1;
      emit_expr (&exp, (unsigned int) nbytes);
      ++c;
      if ((*(input_line_pointer) == '@') && (*(input_line_pointer +1) == 'c'))
	{
	  input_line_pointer +=3;
	  break;
	}
    }
  while ((*input_line_pointer++ == ','));

  /* Put terminator back into stream.  */
  input_line_pointer--;

  demand_empty_rest_of_line ();
}

/* This table describes all the machine specific pseudo-ops
   the assembler has to support.  The fields are:
   *** Pseudo-op name without dot.
   *** Function to call to execute this pseudo-op.
   *** Integer arg to pass to the function.  */

const pseudo_typeS md_pseudo_table[] =
{
  /* In CR16 machine, align is in bytes (not a ptwo boundary).  */
  {"align", s_align_bytes, 0},
  {"long", l_cons,  4 },
  {"4byte", l_cons, 4 },
  {0, 0, 0}
};

/* CR16 relaxation table.  */
const relax_typeS md_relax_table[] =
{
  /* bCC  */
  {0x7f, -0x80, 2, 1},                  /*  8 */
  {0xfffe, -0x10000, 4, 2},             /* 16 */
  {0xfffffe, -0x1000000, 6, 0},         /* 24 */
};

/* Return the bit size for a given operand.  */

static int
get_opbits (operand_type op)
{
  if (op < MAX_OPRD)
    return cr16_optab[op].bit_size;

  return 0;
}

/* Return the argument type of a given operand.  */

static argtype
get_optype (operand_type op)
{
  if (op < MAX_OPRD)
    return cr16_optab[op].arg_type;
  else
    return nullargs;
}

/* Return the flags of a given operand.  */

static int
get_opflags (operand_type op)
{
  if (op < MAX_OPRD)
    return cr16_optab[op].flags;

  return 0;
}

/* Get the cc code.  */

static int
get_cc (char *cc_name)
{
   unsigned int i;

   for (i = 0; i < cr16_num_cc; i++)
     if (strcmp (cc_name, cr16_b_cond_tab[i]) == 0)
       return i;

   return -1;
}

/* Get the core processor register 'reg_name'.  */

static reg
get_register (char *reg_name)
{
  const reg_entry *rreg;

  rreg = (const reg_entry *) str_hash_find (reg_hash, reg_name);

  if (rreg != NULL)
    return rreg->value.reg_val;

  return nullregister;
}
/* Get the core processor register-pair 'reg_name'.  */

static reg
get_register_pair (char *reg_name)
{
  const reg_entry *rreg;
  char tmp_rp[16]="\0";

  /* Add '(' and ')' to the reg pair, if it's not present.  */
  if (reg_name[0] != '(')
    {
      tmp_rp[0] = '(';
      strcat (tmp_rp, reg_name);
      strcat (tmp_rp,")");
      rreg = (const reg_entry *) str_hash_find (regp_hash, tmp_rp);
    }
  else
    rreg = (const reg_entry *) str_hash_find (regp_hash, reg_name);

  if (rreg != NULL)
    return rreg->value.reg_val;

  return nullregister;
}

/* Get the index register 'reg_name'.  */

static reg
get_index_register (char *reg_name)
{
  const reg_entry *rreg;

  rreg = (const reg_entry *) str_hash_find (reg_hash, reg_name);

  if ((rreg != NULL)
      && ((rreg->value.reg_val == 12) || (rreg->value.reg_val == 13)))
    return rreg->value.reg_val;

  return nullregister;
}
/* Get the core processor index register-pair 'reg_name'.  */

static reg
get_index_register_pair (char *reg_name)
{
  const reg_entry *rreg;

  rreg = (const reg_entry *) str_hash_find (regp_hash, reg_name);

  if (rreg != NULL)
    {
      if ((rreg->value.reg_val != 1) || (rreg->value.reg_val != 7)
	  || (rreg->value.reg_val != 9) || (rreg->value.reg_val > 10))
	return rreg->value.reg_val;

      as_bad (_("Unknown register pair - index relative mode: `%d'"), rreg->value.reg_val);
    }

  return nullregister;
}

/* Get the processor register 'preg_name'.  */

static preg
get_pregister (char *preg_name)
{
  const reg_entry *prreg;

  prreg = (const reg_entry *) str_hash_find (preg_hash, preg_name);

  if (prreg != NULL)
    return prreg->value.preg_val;

  return nullpregister;
}

/* Get the processor register 'preg_name 32 bit'.  */

static preg
get_pregisterp (char *preg_name)
{
  const reg_entry *prreg;

  prreg = (const reg_entry *) str_hash_find (pregp_hash, preg_name);

  if (prreg != NULL)
    return prreg->value.preg_val;

  return nullpregister;
}


/* Round up a section size to the appropriate boundary.  */

valueT
md_section_align (segT seg, valueT val)
{
  /* Round .text section to a multiple of 2.  */
  if (seg == text_section)
    return (val + 1) & ~1;
  return val;
}

/* Parse an operand that is machine-specific (remove '*').  */

void
md_operand (expressionS * exp)
{
  char c = *input_line_pointer;

  switch (c)
    {
    case '*':
      input_line_pointer++;
      expression (exp);
      break;
    default:
      break;
    }
}

/* Reset global variables before parsing a new instruction.  */

static void
reset_vars (char *op)
{
  cur_arg_num = relocatable = 0;
  memset (& output_opcode, '\0', sizeof (output_opcode));

  /* Save a copy of the original OP (used in error messages).  */
  strncpy (ins_parse, op, sizeof ins_parse - 1);
  ins_parse [sizeof ins_parse - 1] = 0;
}

/* This macro decides whether a particular reloc is an entry in a
   switch table.  It is used when relaxing, because the linker needs
   to know about all such entries so that it can adjust them if
   necessary.  */

#define SWITCH_TABLE(fix)						\
  ((fix)->fx_addsy != NULL						\
   && (fix)->fx_subsy != NULL						\
   && ((fix)->fx_r_type == BFD_RELOC_CR16_NUM8				\
       || (fix)->fx_r_type == BFD_RELOC_CR16_NUM16			\
       || (fix)->fx_r_type == BFD_RELOC_CR16_NUM32			\
       || (fix)->fx_r_type == BFD_RELOC_CR16_NUM32a)			\
   && S_GET_SEGMENT ((fix)->fx_addsy) != undefined_section		\
   && S_GET_SEGMENT ((fix)->fx_addsy) == S_GET_SEGMENT ((fix)->fx_subsy))

/* See whether we need to force a relocation into the output file.
   This is used to force out switch and PC relative relocations when
   relaxing.  */

int
cr16_force_relocation (fixS *fix)
{
  if (generic_force_reloc (fix) || SWITCH_TABLE (fix))
    return 1;

  return 0;
}

/* Record a fixup for a cons expression.  */

void
cr16_cons_fix_new (fragS *frag, int offset, int len, expressionS *exp,
		   bfd_reloc_code_real_type rtype)
{
  switch (len)
    {
    default: rtype = BFD_RELOC_NONE; break;
    case 1: rtype = BFD_RELOC_CR16_NUM8 ; break;
    case 2: rtype = BFD_RELOC_CR16_NUM16; break;
    case 4:
      if (code_label)
	{
	  rtype = BFD_RELOC_CR16_NUM32a;
	  code_label = 0;
	}
      else
	rtype = BFD_RELOC_CR16_NUM32;
      break;
    }

  fix_new_exp (frag, offset, len, exp, 0, rtype);
}

/* Generate a relocation entry for a fixup.  */

arelent *
tc_gen_reloc (asection *section ATTRIBUTE_UNUSED, fixS * fixP)
{
  arelent * reloc;

  /* If symbols are local and resolved, then no relocation needed.  */
  if ( ((fixP->fx_addsy)
	&& (S_GET_SEGMENT (fixP->fx_addsy) == absolute_section))
       || ((fixP->fx_subsy)
	   && (S_GET_SEGMENT (fixP->fx_subsy) == absolute_section)))
    return NULL;

  reloc = XNEW (arelent);
  reloc->sym_ptr_ptr  = XNEW (asymbol *);
  *reloc->sym_ptr_ptr = symbol_get_bfdsym (fixP->fx_addsy);
  reloc->address = fixP->fx_frag->fr_address + fixP->fx_where;
  reloc->addend = fixP->fx_offset;

  if (fixP->fx_subsy != NULL)
    {
      if (SWITCH_TABLE (fixP))
	{
	  /* Keep the current difference in the addend.  */
	  reloc->addend = (S_GET_VALUE (fixP->fx_addsy)
			   - S_GET_VALUE (fixP->fx_subsy) + fixP->fx_offset);

	  switch (fixP->fx_r_type)
	    {
	    case BFD_RELOC_CR16_NUM8:
	      fixP->fx_r_type = BFD_RELOC_CR16_SWITCH8;
	      break;
	    case BFD_RELOC_CR16_NUM16:
	      fixP->fx_r_type = BFD_RELOC_CR16_SWITCH16;
	      break;
	    case BFD_RELOC_CR16_NUM32:
	      fixP->fx_r_type = BFD_RELOC_CR16_SWITCH32;
	      break;
	    case BFD_RELOC_CR16_NUM32a:
	      fixP->fx_r_type = BFD_RELOC_CR16_NUM32a;
	      break;
	    default:
	      abort ();
	      break;
	    }
	}
      else
	{
	  /* We only resolve difference expressions in the same section.  */
	  as_bad_subtract (fixP);
	  free (reloc->sym_ptr_ptr);
	  free (reloc);
	  return NULL;
	}
    }
#ifdef OBJ_ELF
  if ((fixP->fx_r_type == BFD_RELOC_CR16_GOT_REGREL20)
      && GOT_symbol
      && fixP->fx_addsy == GOT_symbol)
    {
      reloc->addend = fixP->fx_offset = reloc->address;
    }
  else if ((fixP->fx_r_type == BFD_RELOC_CR16_GOTC_REGREL20)
	   && GOT_symbol
	   && fixP->fx_addsy == GOT_symbol)
    {
      reloc->addend = fixP->fx_offset = reloc->address;
    }
#endif

  gas_assert ((int) fixP->fx_r_type > 0);
  reloc->howto = bfd_reloc_type_lookup (stdoutput, fixP->fx_r_type);

  if (reloc->howto == NULL)
    {
      as_bad_where (fixP->fx_file, fixP->fx_line,
		    _("internal error: reloc %d (`%s') not supported by object file format"),
		    fixP->fx_r_type,
		    bfd_get_reloc_code_name (fixP->fx_r_type));
      return NULL;
    }
  gas_assert (!fixP->fx_pcrel == !reloc->howto->pc_relative);

  return reloc;
}

/* Prepare machine-dependent frags for relaxation.  */

int
md_estimate_size_before_relax (fragS *fragp, asection *seg)
{
  /* If symbol is undefined or located in a different section,
     select the largest supported relocation.  */
  relax_substateT subtype;
  relax_substateT rlx_state[] = {0, 2};

  for (subtype = 0; subtype < ARRAY_SIZE (rlx_state); subtype += 2)
    {
      if (fragp->fr_subtype == rlx_state[subtype]
	  && (!S_IS_DEFINED (fragp->fr_symbol)
	      || seg != S_GET_SEGMENT (fragp->fr_symbol)))
	{
	  fragp->fr_subtype = rlx_state[subtype + 1];
	  break;
	}
    }

  if (fragp->fr_subtype >= ARRAY_SIZE (md_relax_table))
    abort ();

  return md_relax_table[fragp->fr_subtype].rlx_length;
}

void
md_convert_frag (bfd *abfd ATTRIBUTE_UNUSED, asection *sec, fragS *fragP)
{
  /* 'opcode' points to the start of the instruction, whether
     we need to change the instruction's fixed encoding.  */
  char *opcode = &fragP->fr_literal[0] + fragP->fr_fix;
  bfd_reloc_code_real_type reloc;

  subseg_change (sec, 0);

  switch (fragP->fr_subtype)
    {
    case 0:
      reloc = BFD_RELOC_CR16_DISP8;
      break;
    case 1:
      /* If the subtype is not changed due to :m operand qualifier,
	 then no need to update the opcode value.  */
      if ((int)opcode[1] != 0x18)
	{
	  opcode[0] = (opcode[0] & 0xf0);
	  opcode[1] = 0x18;
	}
      reloc = BFD_RELOC_CR16_DISP16;
      break;
    case 2:
      /* If the subtype is not changed due to :l operand qualifier,
	 then no need to update the opcode value.  */
      if ((int)opcode[1] != 0)
	{
	  opcode[2] = opcode[0];
	  opcode[0] = opcode[1];
	  opcode[1] = 0x0;
	}
      reloc = BFD_RELOC_CR16_DISP24;
      break;
    default:
      abort();
    }

  fix_new (fragP, fragP->fr_fix,
	   bfd_get_reloc_size (bfd_reloc_type_lookup (stdoutput, reloc)),
	   fragP->fr_symbol, fragP->fr_offset, 1, reloc);
  fragP->fr_var = 0;
  fragP->fr_fix += md_relax_table[fragP->fr_subtype].rlx_length;
}

symbolS *
md_undefined_symbol (char *name)
{
  if (*name == '_' && *(name + 1) == 'G'
      && strcmp (name, "_GLOBAL_OFFSET_TABLE_") == 0)
    {
      if (!GOT_symbol)
	{
	  if (symbol_find (name))
	    as_bad (_("GOT already in symbol table"));
	  GOT_symbol = symbol_new (name, undefined_section,
				   &zero_address_frag, 0);
	}
      return GOT_symbol;
    }
  return 0;
}

/* Process machine-dependent command line options.  Called once for
   each option on the command line that the machine-independent part of
   GAS does not understand.  */

int
md_parse_option (int c ATTRIBUTE_UNUSED, const char *arg ATTRIBUTE_UNUSED)
{
  return 0;
}

/* Machine-dependent usage-output.  */

void
md_show_usage (FILE *stream ATTRIBUTE_UNUSED)
{
  return;
}

const char *
md_atof (int type, char *litP, int *sizeP)
{
  return ieee_md_atof (type, litP, sizeP, target_big_endian);
}

/* Apply a fixS (fixup of an instruction or data that we didn't have
   enough info to complete immediately) to the data in a frag.
   Since linkrelax is nonzero and TC_LINKRELAX_FIXUP is defined to disable
   relaxation of debug sections, this function is called only when
   fixuping relocations of debug sections.  */

void
md_apply_fix (fixS *fixP, valueT *valP, segT seg)
{
  valueT val = * valP;

  if (fixP->fx_addsy == NULL
      && fixP->fx_pcrel == 0)
    fixP->fx_done = 1;
  else if (fixP->fx_pcrel == 1
      && fixP->fx_addsy != NULL
      && S_GET_SEGMENT (fixP->fx_addsy) == seg)
    fixP->fx_done = 1;
  else
    fixP->fx_done = 0;

  if (fixP->fx_addsy != NULL && !fixP->fx_pcrel)
    {
      val = fixP->fx_offset;
      fixP->fx_done = 1;
    }

  if (fixP->fx_done)
    {
      char *buf = fixP->fx_frag->fr_literal + fixP->fx_where;

      fixP->fx_offset = 0;

      switch (fixP->fx_r_type)
	{
	case BFD_RELOC_CR16_NUM8:
	  bfd_put_8 (stdoutput, (unsigned char) val, buf);
	  break;
	case BFD_RELOC_CR16_NUM16:
	  bfd_put_16 (stdoutput, val, buf);
	  break;
	case BFD_RELOC_CR16_NUM32:
	  bfd_put_32 (stdoutput, val, buf);
	  break;
	case BFD_RELOC_CR16_NUM32a:
	  bfd_put_32 (stdoutput, val, buf);
	  break;
	default:
	  /* We shouldn't ever get here because linkrelax is nonzero.  */
	  abort ();
	  break;
	}
      fixP->fx_done = 0;
    }
  else
    fixP->fx_offset = * valP;
}

/* The location from which a PC relative jump should be calculated,
   given a PC relative reloc.  */

long
md_pcrel_from (fixS *fixp)
{
  return fixp->fx_frag->fr_address + fixp->fx_where;
}

static void
initialise_reg_hash_table (htab_t *hash_table,
			   const reg_entry *register_table,
			   const unsigned int num_entries)
{
  const reg_entry *rreg;

  *hash_table = str_htab_create ();

  for (rreg = register_table;
       rreg < (register_table + num_entries);
       rreg++)
    if (str_hash_insert (*hash_table, rreg->name, rreg, 0) != NULL)
      as_fatal (_("duplicate %s"), rreg->name);
}

/* This function is called once, at assembler startup time.  This should
   set up all the tables, etc that the MD part of the assembler needs.  */

void
md_begin (void)
{
  int i = 0;

  /* Set up a hash table for the instructions.  */
  cr16_inst_hash = str_htab_create ();

  while (cr16_instruction[i].mnemonic != NULL)
    {
      const char *mnemonic = cr16_instruction[i].mnemonic;

      if (str_hash_insert (cr16_inst_hash, mnemonic, cr16_instruction + i, 0))
	as_fatal (_("duplicate %s"), mnemonic);

      /* Insert unique names into hash table.  The CR16 instruction set
	 has many identical opcode names that have different opcodes based
	 on the operands.  This hash table then provides a quick index to
	 the first opcode with a particular name in the opcode table.  */
      do
	{
	  ++i;
	}
      while (cr16_instruction[i].mnemonic != NULL
	     && streq (cr16_instruction[i].mnemonic, mnemonic));
    }

  /* Initialize reg_hash hash table.  */
  initialise_reg_hash_table (& reg_hash, cr16_regtab, NUMREGS);
  /* Initialize regp_hash hash table.  */
  initialise_reg_hash_table (& regp_hash, cr16_regptab, NUMREGPS);
  /* Initialize preg_hash hash table.  */
  initialise_reg_hash_table (& preg_hash, cr16_pregtab, NUMPREGS);
  /* Initialize pregp_hash hash table.  */
  initialise_reg_hash_table (& pregp_hash, cr16_pregptab, NUMPREGPS);

  /*  Set linkrelax here to avoid fixups in most sections.  */
  linkrelax = 1;
}

/* Process constants (immediate/absolute)
   and labels (jump targets/Memory locations).  */

static void
process_label_constant (char *str, ins * cr16_ins)
{
  char *saved_input_line_pointer;
  int symbol_with_at = 0;
  int symbol_with_s = 0;
  int symbol_with_m = 0;
  int symbol_with_l = 0;
  int symbol_with_at_got = 0;
  int symbol_with_at_gotc = 0;
  argument *cur_arg = cr16_ins->arg + cur_arg_num;  /* Current argument.  */

  saved_input_line_pointer = input_line_pointer;
  input_line_pointer = str;

  expression (&cr16_ins->exp);

  switch (cr16_ins->exp.X_op)
    {
    case O_big:
    case O_absent:
      /* Missing or bad expr becomes absolute 0.  */
      as_bad (_("missing or invalid displacement expression `%s' taken as 0"),
	      str);
      cr16_ins->exp.X_op = O_constant;
      cr16_ins->exp.X_add_number = 0;
      cr16_ins->exp.X_add_symbol = NULL;
      cr16_ins->exp.X_op_symbol = NULL;
      /* Fall through.  */

    case O_constant:
      cur_arg->X_op = O_constant;
      cur_arg->constant = cr16_ins->exp.X_add_number;
      break;

    case O_symbol:
    case O_subtract:
    case O_add:
      cur_arg->X_op = O_symbol;
      cur_arg->constant = cr16_ins->exp.X_add_number;
      cr16_ins->exp.X_add_number = 0;
      cr16_ins->rtype = BFD_RELOC_NONE;
      relocatable = 1;

      if (startswith (input_line_pointer, "@c"))
	symbol_with_at = 1;

      if (startswith (input_line_pointer, "@l")
	  || startswith (input_line_pointer, ":l"))
	symbol_with_l = 1;

      if (startswith (input_line_pointer, "@m")
	  || startswith (input_line_pointer, ":m"))
	symbol_with_m = 1;

      if (startswith (input_line_pointer, "@s")
	  || startswith (input_line_pointer, ":s"))
	symbol_with_s = 1;

      if (startswith (input_line_pointer, "@cGOT")
	  || startswith (input_line_pointer, "@cgot"))
	{
	  if (GOT_symbol == NULL)
	    GOT_symbol = symbol_find_or_make (GLOBAL_OFFSET_TABLE_NAME);

	  symbol_with_at_gotc = 1;
	}
      else if (startswith (input_line_pointer, "@GOT")
	       || startswith (input_line_pointer, "@got"))
	{
	  if ((startswith (input_line_pointer, "+"))
	      || (startswith (input_line_pointer, "-")))
	    as_warn (_("GOT bad expression with %s."), input_line_pointer);

	  if (GOT_symbol == NULL)
	    GOT_symbol = symbol_find_or_make (GLOBAL_OFFSET_TABLE_NAME);

	  symbol_with_at_got = 1;
	}

      switch (cur_arg->type)
	{
	case arg_cr:
	  if (IS_INSN_TYPE (LD_STOR_INS) || IS_INSN_TYPE (CSTBIT_INS))
	    {
	      if (symbol_with_at_got)
		cr16_ins->rtype = BFD_RELOC_CR16_GOT_REGREL20;
	      else if (symbol_with_at_gotc)
		cr16_ins->rtype = BFD_RELOC_CR16_GOTC_REGREL20;
	      else if (cur_arg->size == 20)
		cr16_ins->rtype = BFD_RELOC_CR16_REGREL20;
	      else
		cr16_ins->rtype = BFD_RELOC_CR16_REGREL20a;
	    }
	  break;

	case arg_crp:
	  if (IS_INSN_TYPE (LD_STOR_INS) || IS_INSN_TYPE (CSTBIT_INS))
	    {
	      if (symbol_with_at_got)
		cr16_ins->rtype = BFD_RELOC_CR16_GOT_REGREL20;
	      else if (symbol_with_at_gotc)
		cr16_ins->rtype = BFD_RELOC_CR16_GOTC_REGREL20;
	    } else {
	    switch (instruction->size)
	      {
	      case 1:
		switch (cur_arg->size)
		  {
		  case 0:
		    cr16_ins->rtype = BFD_RELOC_CR16_REGREL0;
		    break;
		  case 4:
		    if (IS_INSN_MNEMONIC ("loadb") || IS_INSN_MNEMONIC ("storb"))
		      cr16_ins->rtype = BFD_RELOC_CR16_REGREL4;
		    else
		      cr16_ins->rtype = BFD_RELOC_CR16_REGREL4a;
		    break;
		  default: break;
		  }
		break;
	      case 2:
		cr16_ins->rtype = BFD_RELOC_CR16_REGREL16;
		break;
	      case 3:
		if (cur_arg->size == 20)
		  cr16_ins->rtype = BFD_RELOC_CR16_REGREL20;
		else
		  cr16_ins->rtype = BFD_RELOC_CR16_REGREL20a;
		break;
	      default:
		break;
	      }
	  }
	  break;

	case arg_idxr:
	  if (IS_INSN_TYPE (LD_STOR_INS) || IS_INSN_TYPE (CSTBIT_INS))
	    {
	      if (symbol_with_at_got)
		cr16_ins->rtype = BFD_RELOC_CR16_GOT_REGREL20;
	      else if (symbol_with_at_gotc)
		cr16_ins->rtype = BFD_RELOC_CR16_GOTC_REGREL20;
	      else
		cr16_ins->rtype = BFD_RELOC_CR16_REGREL20;
	    }
	  break;

	case arg_idxrp:
	  if (IS_INSN_TYPE (LD_STOR_INS) || IS_INSN_TYPE (CSTBIT_INS))
	    {
	      if (symbol_with_at_got)
		cr16_ins->rtype = BFD_RELOC_CR16_GOT_REGREL20;
	      else if (symbol_with_at_gotc)
		cr16_ins->rtype = BFD_RELOC_CR16_GOTC_REGREL20;
	      else {
		switch (instruction->size)
		  {
		  case 1: cr16_ins->rtype = BFD_RELOC_CR16_REGREL0; break;
		  case 2: cr16_ins->rtype = BFD_RELOC_CR16_REGREL14; break;
		  case 3: cr16_ins->rtype = BFD_RELOC_CR16_REGREL20; break;
		  default: break;
		  }
	      }
	    }
	  break;

	case arg_c:
	  if (IS_INSN_MNEMONIC ("bal"))
	    cr16_ins->rtype = BFD_RELOC_CR16_DISP24;
	  else if (IS_INSN_TYPE (BRANCH_INS))
	    {
	      if (symbol_with_l)
		cr16_ins->rtype = BFD_RELOC_CR16_DISP24;
	      else if (symbol_with_m)
		cr16_ins->rtype = BFD_RELOC_CR16_DISP16;
	      else
		cr16_ins->rtype = BFD_RELOC_CR16_DISP8;
	    }
	  else if (IS_INSN_TYPE (STOR_IMM_INS) || IS_INSN_TYPE (LD_STOR_INS)
		   || IS_INSN_TYPE (CSTBIT_INS))
	    {
	      if (symbol_with_s)
		as_bad (_("operand %d: illegal use expression: `%s`"), cur_arg_num + 1, str);
	      if (symbol_with_at_got)
		cr16_ins->rtype = BFD_RELOC_CR16_GOT_REGREL20;
	      else if (symbol_with_at_gotc)
		cr16_ins->rtype = BFD_RELOC_CR16_GOTC_REGREL20;
	      else if (symbol_with_m)
		cr16_ins->rtype = BFD_RELOC_CR16_ABS20;
	      else /* Default to (symbol_with_l) */
		cr16_ins->rtype = BFD_RELOC_CR16_ABS24;
	    }
	  else if (IS_INSN_TYPE (BRANCH_NEQ_INS))
	    cr16_ins->rtype = BFD_RELOC_CR16_DISP4;
	  break;

	case arg_ic:
	  if (IS_INSN_TYPE (ARITH_INS))
	    {
	      if (symbol_with_at_got)
		cr16_ins->rtype = BFD_RELOC_CR16_GOT_REGREL20;
	      else if (symbol_with_at_gotc)
		cr16_ins->rtype = BFD_RELOC_CR16_GOTC_REGREL20;
	      else if (symbol_with_s)
		cr16_ins->rtype = BFD_RELOC_CR16_IMM4;
	      else if (symbol_with_m)
		cr16_ins->rtype = BFD_RELOC_CR16_IMM20;
	      else if (symbol_with_at)
		cr16_ins->rtype = BFD_RELOC_CR16_IMM32a;
	      else /* Default to (symbol_with_l) */
		cr16_ins->rtype = BFD_RELOC_CR16_IMM32;
	    }
	  else if (IS_INSN_TYPE (ARITH_BYTE_INS))
	    {
	      cr16_ins->rtype = BFD_RELOC_CR16_IMM16;
	    }
	  break;
	default:
	  break;
	}
      break;

    default:
      cur_arg->X_op = cr16_ins->exp.X_op;
      break;
    }

  input_line_pointer = saved_input_line_pointer;
  return;
}

/* Retrieve the opcode image of a given register.
   If the register is illegal for the current instruction,
   issue an error.  */

static int
getreg_image (reg r)
{
  const reg_entry *rreg;
  char *reg_name;
  int is_procreg = 0; /* Nonzero means argument should be processor reg.  */

  /* Check whether the register is in registers table.  */
  if (r < MAX_REG)
    rreg = cr16_regtab + r;
  else /* Register not found.  */
    {
      as_bad (_("Unknown register: `%d'"), r);
      return 0;
    }

  reg_name = rreg->name;

  /* Issue a error message when register is illegal.  */
#define IMAGE_ERR						\
  as_bad (_("Illegal register (`%s') in Instruction: `%s'"),	\
	  reg_name, ins_parse);

  switch (rreg->type)
    {
    case CR16_R_REGTYPE:
      if (! is_procreg)
	return rreg->image;
      else
	IMAGE_ERR;
      break;

    case CR16_P_REGTYPE:
      return rreg->image;
      break;

    default:
      IMAGE_ERR;
      break;
    }

  return 0;
}

/* Parsing different types of operands
   -> constants             Immediate/Absolute/Relative numbers
   -> Labels                Relocatable symbols
   -> (reg pair base)       Register pair base
   -> (rbase)               Register base
   -> disp(rbase)           Register relative
   -> [rinx]disp(reg pair)  Register index with reg pair mode
   -> disp(rbase,ridx,scl)  Register index mode.  */

static void
set_operand (char *operand, ins * cr16_ins)
{
  char *operandS; /* Pointer to start of sub-operand.  */
  char *operandE; /* Pointer to end of sub-operand.  */

  argument *cur_arg = &cr16_ins->arg[cur_arg_num]; /* Current argument.  */

  /* Initialize pointers.  */
  operandS = operandE = operand;

  switch (cur_arg->type)
    {
    case arg_ic:    /* Case $0x18.  */
      operandS++;
      /* Fall through.  */
    case arg_c:     /* Case 0x18.  */
      /* Set constant.  */
      process_label_constant (operandS, cr16_ins);

      if (cur_arg->type != arg_ic)
	cur_arg->type = arg_c;
      break;

    case arg_icr:   /* Case $0x18(r1).  */
      operandS++;
    case arg_cr:    /* Case 0x18(r1).   */
      /* Set displacement constant.  */
      while (*operandE != '(')
	operandE++;
      *operandE = '\0';
      process_label_constant (operandS, cr16_ins);
      operandS = operandE;
      /* Fall through.  */
    case arg_rbase: /* Case (r1) or (r1,r0).  */
      operandS++;
      /* Set register base.  */
      while (*operandE != ')')
	operandE++;
      *operandE = '\0';
      if ((cur_arg->r = get_register (operandS)) == nullregister)
	as_bad (_("Illegal register `%s' in Instruction `%s'"),
		operandS, ins_parse);

      /* set the arg->rp, if reg is "r12" or "r13" or "14" or "15" */
      if ((cur_arg->type != arg_rbase)
	  && ((getreg_image (cur_arg->r) == 12)
	      || (getreg_image (cur_arg->r) == 13)
	      || (getreg_image (cur_arg->r) == 14)
	      || (getreg_image (cur_arg->r) == 15)))
	{
	  cur_arg->type = arg_crp;
	  cur_arg->rp = cur_arg->r;
	}
      break;

    case arg_crp:    /* Case 0x18(r1,r0).   */
      /* Set displacement constant.  */
      while (*operandE != '(')
	operandE++;
      *operandE = '\0';
      process_label_constant (operandS, cr16_ins);
      operandS = operandE;
      operandS++;
      /* Set register pair base.  */
      while (*operandE != ')')
	operandE++;
      *operandE = '\0';
      if ((cur_arg->rp = get_register_pair (operandS)) == nullregister)
	as_bad (_("Illegal register pair `%s' in Instruction `%s'"),
		operandS, ins_parse);
      break;

    case arg_idxr:
      /* Set register pair base.  */
      if ((strchr (operandS,'(') != NULL))
	{
	  while ((*operandE != '(') && (! ISSPACE (*operandE)))
	    operandE++;
	  if ((cur_arg->rp = get_index_register_pair (operandE)) == nullregister)
	    as_bad (_("Illegal register pair `%s' in Instruction `%s'"),
		    operandS, ins_parse);
	  *operandE++ = '\0';
	  cur_arg->type = arg_idxrp;
	}
      else
	cur_arg->rp = -1;

      operandE = operandS;
      /* Set displacement constant.  */
      while (*operandE != ']')
	operandE++;
      process_label_constant (++operandE, cr16_ins);
      *operandE++ = '\0';
      operandE = operandS;

      /* Set index register .  */
      operandS = strchr (operandE,'[');
      if (operandS != NULL)
	{ /* Eliminate '[', detach from rest of operand.  */
	  *operandS++ = '\0';

	  operandE = strchr (operandS, ']');

	  if (operandE == NULL)
	    as_bad (_("unmatched '['"));
	  else
	    { /* Eliminate ']' and make sure it was the last thing
		 in the string.  */
	      *operandE = '\0';
	      if (*(operandE + 1) != '\0')
		as_bad (_("garbage after index spec ignored"));
	    }
	}

      if ((cur_arg->i_r = get_index_register (operandS)) == nullregister)
	as_bad (_("Illegal register `%s' in Instruction `%s'"),
		operandS, ins_parse);
      *operandE = '\0';
      *operandS = '\0';
      break;

    default:
      break;
    }
}

/* Parse a single operand.
   operand - Current operand to parse.
   cr16_ins - Current assembled instruction.  */

static void
parse_operand (char *operand, ins * cr16_ins)
{
  int ret_val;
  argument *cur_arg = cr16_ins->arg + cur_arg_num; /* Current argument.  */

  /* Initialize the type to NULL before parsing.  */
  cur_arg->type = nullargs;

  /* Check whether this is a condition code .  */
  if ((IS_INSN_MNEMONIC ("b")) && ((ret_val = get_cc (operand)) != -1))
    {
      cur_arg->type = arg_cc;
      cur_arg->cc = ret_val;
      cur_arg->X_op = O_register;
      return;
    }

  /* Check whether this is a general processor register.  */
  if ((ret_val = get_register (operand)) != nullregister)
    {
      cur_arg->type = arg_r;
      cur_arg->r = ret_val;
      cur_arg->X_op = 0;
      return;
    }

  /* Check whether this is a general processor register pair.  */
  if ((operand[0] == '(')
      && ((ret_val = get_register_pair (operand)) != nullregister))
    {
      cur_arg->type = arg_rp;
      cur_arg->rp = ret_val;
      cur_arg->X_op = O_register;
      return;
    }

  /* Check whether the operand is a processor register.
     For "lprd" and "sprd" instruction, only 32 bit
     processor registers used.  */
  if (!(IS_INSN_MNEMONIC ("lprd") || (IS_INSN_MNEMONIC ("sprd")))
      && ((ret_val = get_pregister (operand)) != nullpregister))
    {
      cur_arg->type = arg_pr;
      cur_arg->pr = ret_val;
      cur_arg->X_op = O_register;
      return;
    }

  /* Check whether this is a processor register - 32 bit.  */
  if ((ret_val = get_pregisterp (operand)) != nullpregister)
    {
      cur_arg->type = arg_prp;
      cur_arg->prp = ret_val;
      cur_arg->X_op = O_register;
      return;
    }

  /* Deal with special characters.  */
  switch (operand[0])
    {
    case '$':
      if (strchr (operand, '(') != NULL)
	cur_arg->type = arg_icr;
      else
	cur_arg->type = arg_ic;
      goto set_params;
      break;

    case '(':
      cur_arg->type = arg_rbase;
      goto set_params;
      break;

    case '[':
      cur_arg->type = arg_idxr;
      goto set_params;
      break;

    default:
      break;
    }

  if (strchr (operand, '(') != NULL)
    {
      if (strchr (operand, ',') != NULL
	  && (strchr (operand, ',') > strchr (operand, '(')))
	cur_arg->type = arg_crp;
      else
	cur_arg->type = arg_cr;
    }
  else
    cur_arg->type = arg_c;

  /* Parse an operand according to its type.  */
 set_params:
  cur_arg->constant = 0;
  set_operand (operand, cr16_ins);
}

/* Parse the various operands. Each operand is then analyzed to fillup
   the fields in the cr16_ins data structure.  */

static void
parse_operands (ins * cr16_ins, char *operands)
{
  char *operandS;            /* Operands string.  */
  char *operandH, *operandT; /* Single operand head/tail pointers.  */
  int allocated = 0;         /* Indicates a new operands string was allocated.*/
  char *operand[MAX_OPERANDS];/* Separating the operands.  */
  int op_num = 0;             /* Current operand number we are parsing.  */
  int bracket_flag = 0;       /* Indicates a bracket '(' was found.  */
  int sq_bracket_flag = 0;    /* Indicates a square bracket '[' was found.  */

  /* Preprocess the list of registers, if necessary.  */
  operandS = operandH = operandT = operands;

  while (*operandT != '\0')
    {
      if (*operandT == ',' && bracket_flag != 1 && sq_bracket_flag != 1)
	{
	  *operandT++ = '\0';
	  operand[op_num++] = strdup (operandH);
	  operandH = operandT;
	  continue;
	}

      if (*operandT == ' ')
	as_bad (_("Illegal operands (whitespace): `%s'"), ins_parse);

      if (*operandT == '(')
	bracket_flag = 1;
      else if (*operandT == '[')
	sq_bracket_flag = 1;

      if (*operandT == ')')
	{
	  if (bracket_flag)
	    bracket_flag = 0;
	  else
	    as_fatal (_("Missing matching brackets : `%s'"), ins_parse);
	}
      else if (*operandT == ']')
	{
	  if (sq_bracket_flag)
	    sq_bracket_flag = 0;
	  else
	    as_fatal (_("Missing matching brackets : `%s'"), ins_parse);
	}

      if (bracket_flag == 1 && *operandT == ')')
	bracket_flag = 0;
      else if (sq_bracket_flag == 1 && *operandT == ']')
	sq_bracket_flag = 0;

      operandT++;
    }

  /* Adding the last operand.  */
  operand[op_num++] = strdup (operandH);
  cr16_ins->nargs = op_num;

  /* Verifying correct syntax of operands (all brackets should be closed).  */
  if (bracket_flag || sq_bracket_flag)
    as_fatal (_("Missing matching brackets : `%s'"), ins_parse);

  /* Now we parse each operand separately.  */
  for (op_num = 0; op_num < cr16_ins->nargs; op_num++)
    {
      cur_arg_num = op_num;
      parse_operand (operand[op_num], cr16_ins);
      free (operand[op_num]);
    }

  if (allocated)
    free (operandS);
}

/* Get the trap index in dispatch table, given its name.
   This routine is used by assembling the 'excp' instruction.  */

static int
gettrap (char *s)
{
  const trap_entry *trap;

  for (trap = cr16_traps; trap < (cr16_traps + NUMTRAPS); trap++)
    if (strcasecmp (trap->name, s) == 0)
      return trap->entry;

  /* To make compatible with CR16 4.1 tools, the below 3-lines of
   * code added. Refer: Development Tracker item #123 */
  for (trap = cr16_traps; trap < (cr16_traps + NUMTRAPS); trap++)
    if (trap->entry  == (unsigned int) atoi (s))
      return trap->entry;

  as_bad (_("Unknown exception: `%s'"), s);
  return 0;
}

/* Top level module where instruction parsing starts.
   cr16_ins - data structure holds some information.
   operands - holds the operands part of the whole instruction.  */

static void
parse_insn (ins *insn, char *operands)
{
  int i;

  /* Handle instructions with no operands.  */
  for (i = 0; cr16_no_op_insn[i] != NULL; i++)
  {
    if (streq (cr16_no_op_insn[i], instruction->mnemonic))
    {
      insn->nargs = 0;
      return;
    }
  }

  /* Handle 'excp' instructions.  */
  if (IS_INSN_MNEMONIC ("excp"))
    {
      insn->nargs = 1;
      insn->arg[0].type = arg_ic;
      insn->arg[0].constant = gettrap (operands);
      insn->arg[0].X_op = O_constant;
      return;
    }

  if (operands != NULL)
    parse_operands (insn, operands);
}

/* bCC instruction requires special handling.  */
static char *
get_b_cc (char * op)
{
  unsigned int i;

  if (op[1] == 0 || (op[2] != 0 && op[3] != 0))
    return NULL;

  for (i = 0; i < cr16_num_cc ; i++)
    if (streq (op + 1, cr16_b_cond_tab[i]))
      return (char *) cr16_b_cond_tab[i];

   return NULL;
}

/* bCC instruction requires special handling.  */
static int
is_bcc_insn (char * op)
{
  if (!(streq (op, "bal") || streq (op, "beq0b") || streq (op, "bnq0b")
	|| streq (op, "beq0w") || streq (op, "bnq0w")))
    if ((op[0] == 'b') && (get_b_cc (op) != NULL))
      return 1;
  return 0;
}

/* Cinv instruction requires special handling.  */

static void
check_cinv_options (char * operand)
{
  char *p = operand;

  while (*++p != ']')
    {
      switch (*p)
	{
	case ',':
	case ' ':
	case 'i':
	case 'u':
	case 'd':
	  break;
	default:
	  as_bad (_("Illegal `cinv' parameter: `%c'"), *p);
	}
    }
}

/* Retrieve the opcode image of a given register pair.
   If the register is illegal for the current instruction,
   issue an error.  */

static int
getregp_image (reg r)
{
  const reg_entry *rreg;
  char *reg_name;

  /* Check whether the register is in registers table.  */
  if (r < MAX_REG)
    rreg = cr16_regptab + r;
  /* Register not found.  */
  else
    {
      as_bad (_("Unknown register pair: `%d'"), r);
      return 0;
    }

  reg_name = rreg->name;

  /* Issue a error message when register  pair is illegal.  */
#define RPAIR_IMAGE_ERR							\
  as_bad (_("Illegal register pair (`%s') in Instruction: `%s'"),	\
	  reg_name, ins_parse);						\
  break;

  switch (rreg->type)
    {
    case CR16_RP_REGTYPE:
      return rreg->image;
    default:
      RPAIR_IMAGE_ERR;
    }

  return 0;
}

/* Retrieve the opcode image of a given index register pair.
   If the register is illegal for the current instruction,
   issue an error.  */

static int
getidxregp_image (reg r)
{
  const reg_entry *rreg;
  char *reg_name;

  /* Check whether the register is in registers table.  */
  if (r < MAX_REG)
    rreg = cr16_regptab + r;
  /* Register not found.  */
  else
    {
      as_bad (_("Unknown register pair: `%d'"), r);
      return 0;
    }

  reg_name = rreg->name;

  /* Issue a error message when register  pair is illegal.  */
#define IDX_RPAIR_IMAGE_ERR						\
  as_bad (_("Illegal index register pair (`%s') in Instruction: `%s'"), \
	  reg_name, ins_parse);						\

  if (rreg->type == CR16_RP_REGTYPE)
    {
      switch (rreg->image)
	{
	case 0:  return 0; break;
	case 2:  return 1; break;
	case 4:  return 2; break;
	case 6:  return 3; break;
	case 8:  return 4; break;
	case 10: return 5; break;
	case 3:  return 6; break;
	case 5:  return 7; break;
	default:
	  break;
	}
    }

  IDX_RPAIR_IMAGE_ERR;
  return 0;
}

/* Retrieve the opcode image of a given processor register.
   If the register is illegal for the current instruction,
   issue an error.  */
static int
getprocreg_image (int r)
{
  const reg_entry *rreg;
  char *reg_name;

  /* Check whether the register is in registers table.  */
  if (r >= MAX_REG && r < MAX_PREG)
    rreg = &cr16_pregtab[r - MAX_REG];
  /* Register not found.  */
  else
    {
      as_bad (_("Unknown processor register : `%d'"), r);
      return 0;
    }

  reg_name = rreg->name;

  /* Issue a error message when register  pair is illegal.  */
#define PROCREG_IMAGE_ERR						\
  as_bad (_("Illegal processor register (`%s') in Instruction: `%s'"),	\
	  reg_name, ins_parse);						\
  break;

  switch (rreg->type)
    {
    case CR16_P_REGTYPE:
      return rreg->image;
    default:
      PROCREG_IMAGE_ERR;
    }

  return 0;
}

/* Retrieve the opcode image of a given processor register.
   If the register is illegal for the current instruction,
   issue an error.  */
static int
getprocregp_image (int r)
{
  const reg_entry *rreg;
  char *reg_name;
  int pregptab_disp = 0;

  /* Check whether the register is in registers table.  */
  if (r >= MAX_REG && r < MAX_PREG)
    {
      r = r - MAX_REG;
      switch (r)
	{
	case 4: pregptab_disp = 1;  break;
	case 6: pregptab_disp = 2;  break;
	case 8:
	case 9:
	case 10:
	  pregptab_disp = 3;  break;
	case 12:
	  pregptab_disp = 4;  break;
	case 14:
	  pregptab_disp = 5;  break;
	default: break;
	}
      rreg = &cr16_pregptab[r - pregptab_disp];
    }
  /* Register not found.  */
  else
    {
      as_bad (_("Unknown processor register (32 bit) : `%d'"), r);
      return 0;
    }

  reg_name = rreg->name;

  /* Issue a error message when register  pair is illegal.  */
#define PROCREGP_IMAGE_ERR						\
  as_bad (_("Illegal 32 bit - processor register (`%s') in Instruction: `%s'"), \
	  reg_name, ins_parse);						\
  break;

  switch (rreg->type)
    {
    case CR16_P_REGTYPE:
      return rreg->image;
    default:
      PROCREGP_IMAGE_ERR;
    }

  return 0;
}

/* Routine used to represent integer X using NBITS bits.  */

static long
getconstant (long x, int nbits)
{
  if ((unsigned) nbits >= sizeof (x) * CHAR_BIT)
    return x;
  return x & ((1UL << nbits) - 1);
}

/* Print a constant value to 'output_opcode':
   ARG holds the operand's type and value.
   SHIFT represents the location of the operand to be print into.
   NBITS determines the size (in bits) of the constant.  */

static void
print_constant (int nbits, int shift, argument *arg)
{
  unsigned long mask = 0;
  unsigned long constant = getconstant (arg->constant, nbits);

  switch (nbits)
    {
    case 32:
    case 28:
      /* mask the upper part of the constant, that is, the bits
	 going to the lowest byte of output_opcode[0].
	 The upper part of output_opcode[1] is always filled,
	 therefore it is always masked with 0xFFFF.  */
      mask = (1 << (nbits - 16)) - 1;
      /* Divide the constant between two consecutive words :
	 0        1         2         3
	 +---------+---------+---------+---------+
	 |         | X X X X | x X x X |         |
	 +---------+---------+---------+---------+
	 output_opcode[0]    output_opcode[1]     */

      CR16_PRINT (0, (constant >> WORD_SHIFT) & mask, 0);
      CR16_PRINT (1, constant & 0xFFFF, WORD_SHIFT);
      break;

    case 21:
      if ((nbits == 21) && (IS_INSN_TYPE (LD_STOR_INS)))
	nbits = 20;
      /* Fall through.  */
    case 24:
    case 22:
    case 20:
      /* mask the upper part of the constant, that is, the bits
	 going to the lowest byte of output_opcode[0].
	 The upper part of output_opcode[1] is always filled,
	 therefore it is always masked with 0xFFFF.  */
      mask = (1 << (nbits - 16)) - 1;
      /* Divide the constant between two consecutive words :
	 0        1         2          3
	 +---------+---------+---------+---------+
	 |         | X X X X | - X - X |         |
	 +---------+---------+---------+---------+
	 output_opcode[0]    output_opcode[1]     */

      if (instruction->size > 2 && shift == WORD_SHIFT)
	{
	  if (arg->type == arg_idxrp)
	    {
	      CR16_PRINT (0, ((constant >> WORD_SHIFT) & mask) << 8, 0);
	      CR16_PRINT (1, constant & 0xFFFF, WORD_SHIFT);
	    }
	  else
	    {
	      CR16_PRINT (0,
			  ((((constant >> WORD_SHIFT) & mask & 0xf) << 8)
			   | (((constant >> WORD_SHIFT) & mask & 0xf0) >> 4)),
			  0);
	      CR16_PRINT (1, constant & 0xFFFF, WORD_SHIFT);
	    }
	}
      else
	CR16_PRINT (0, constant, shift);
      break;

    case 14:
      if (arg->type == arg_idxrp)
	{
	  if (instruction->size == 2)
	    {
	      CR16_PRINT (0, (constant)      & 0xf, shift);      /* 0-3 bits.  */
	      CR16_PRINT (0, (constant >> 4) & 0x3, shift + 20); /* 4-5 bits.  */
	      CR16_PRINT (0, (constant >> 6) & 0x3, shift + 14); /* 6-7 bits.  */
	      CR16_PRINT (0, (constant >> 8) & 0x3f, shift + 8); /* 8-13 bits.  */
	    }
	  else
	    CR16_PRINT (0, constant, shift);
	}
      break;

    case 16:
    case 12:
      /* When instruction size is 3 and 'shift' is 16, a 16-bit constant is
	 always filling the upper part of output_opcode[1]. If we mistakenly
	 write it to output_opcode[0], the constant prefix (that is, 'match')
	 will be overridden.
	 0        1         2         3
	 +---------+---------+---------+---------+
	 | 'match' |         | X X X X |         |
	 +---------+---------+---------+---------+
	 output_opcode[0]    output_opcode[1]     */

      if (instruction->size > 2 && shift == WORD_SHIFT)
	CR16_PRINT (1, constant, WORD_SHIFT);
      else
	CR16_PRINT (0, constant, shift);
      break;

    case 8:
      CR16_PRINT (0, (constant / 2) & 0xf, shift);
      CR16_PRINT (0, (constant / 2) >> 4, shift + 8);
      break;

    default:
      CR16_PRINT (0, constant, shift);
      break;
    }
}

/* Print an operand to 'output_opcode', which later on will be
   printed to the object file:
   ARG holds the operand's type, size and value.
   SHIFT represents the printing location of operand.
   NBITS determines the size (in bits) of a constant operand.  */

static void
print_operand (int nbits, int shift, argument *arg)
{
  switch (arg->type)
    {
    case arg_cc:
      CR16_PRINT (0, arg->cc, shift);
      break;

    case arg_r:
      CR16_PRINT (0, getreg_image (arg->r), shift);
      break;

    case arg_rp:
      CR16_PRINT (0, getregp_image (arg->rp), shift);
      break;

    case arg_pr:
      CR16_PRINT (0, getprocreg_image (arg->pr), shift);
      break;

    case arg_prp:
      CR16_PRINT (0, getprocregp_image (arg->prp), shift);
      break;

    case arg_idxrp:
      /*    16      12      8    6      0
	    +-----------------------------+
	    | r_index | disp  | rp_base   |
	    +-----------------------------+          */

      if (instruction->size == 3)
	{
	  CR16_PRINT (0, getidxregp_image (arg->rp), 0);
	  CR16_PRINT (0, getreg_image (arg->i_r) & 1, 3);
	}
      else
	{
	  CR16_PRINT (0, getidxregp_image (arg->rp), 16);
	  CR16_PRINT (0, getreg_image (arg->i_r) & 1, 19);
	}
      print_constant (nbits, shift, arg);
      break;

    case arg_idxr:
      CR16_PRINT (0, getreg_image (arg->i_r) & 1,
		  (IS_INSN_TYPE (CSTBIT_INS)
		   && instruction->mnemonic[4] == 'b') ? 23 : 24);
      print_constant (nbits, shift, arg);
      break;

    case arg_ic:
    case arg_c:
      print_constant (nbits, shift, arg);
      break;

    case arg_rbase:
      CR16_PRINT (0, getreg_image (arg->r), shift);
      break;

    case arg_cr:
      print_constant (nbits, shift, arg);
      /* Add the register argument to the output_opcode.  */
      CR16_PRINT (0, getreg_image (arg->r), shift - 16);
      break;

    case arg_crp:
      print_constant (nbits, shift, arg);
      if ((IS_INSN_TYPE (LD_STOR_INS) || IS_INSN_TYPE (CSTBIT_INS))
	  && instruction->size == 1)
	CR16_PRINT (0, getregp_image (arg->rp), 16);
      else if (instruction->size > 1)
	CR16_PRINT (0, getregp_image (arg->rp), (shift + 16) & 31);
      else
	CR16_PRINT (0, getregp_image (arg->rp), shift);
      break;

    default:
      break;
    }
}

/* Retrieve the number of operands for the current assembled instruction.  */

static int
get_number_of_operands (void)
{
  int i;

  for (i = 0; instruction->operands[i].op_type && i < MAX_OPERANDS; i++)
    ;
  return i;
}

/* Verify that the number NUM can be represented in BITS bits (that is,
   within its permitted range), based on the instruction's FLAGS.
   If UPDATE is nonzero, update the value of NUM if necessary.
   Return OP_LEGAL upon success, actual error type upon failure.  */

static op_err
check_range (long *num, int bits, int unsigned flags, int update)
{
  int32_t min, max;
  op_err retval = OP_LEGAL;
  int32_t value = *num;

  /* Verify operand value is even.  */
  if (flags & OP_EVEN)
    {
      if (value % 2)
	return OP_NOT_EVEN;
    }

  if (flags & OP_DEC)
    {
      value -= 1;
      if (update)
	*num = value;
    }

  if (flags & OP_SHIFT)
    {
      value >>= 1;
      if (update)
	*num = value;
    }
  else if (flags & OP_SHIFT_DEC)
    {
      value = (value >> 1) - 1;
      if (update)
	*num = value;
    }

  if (flags & OP_ABS20)
    {
      if (value > 0xEFFFF)
	return OP_OUT_OF_RANGE;
    }

  if (flags & OP_ESC)
    {
      if (value == 0xB || value == 0x9)
	return OP_OUT_OF_RANGE;
      else if (value == -1)
	{
	  if (update)
	    *num = 9;
	  return retval;
	}
    }

  if (flags & OP_ESC1)
    {
      if (value > 13)
	return OP_OUT_OF_RANGE;
    }

  if (bits == 0)
    {
      if (value != 0)
	retval = OP_OUT_OF_RANGE;
      return retval;
    }

  if (flags & OP_SIGNED)
    {
      max = (1U << (bits - 1)) - 1;
      min = - (1U << (bits - 1));
      if (value > max || value < min)
	retval = OP_OUT_OF_RANGE;
    }
  else if (flags & OP_UNSIGNED)
    {
      max = (1U << (bits - 1) << 1) - 1;
      if ((uint32_t) value > (uint32_t) max)
	retval = OP_OUT_OF_RANGE;
    }
  else if (flags & OP_NEG)
    {
      min = - ((1U << (bits - 1)) - 1);
      if (value < min)
	retval = OP_OUT_OF_RANGE;
    }
  return retval;
}

/* Bunch of error checking.
   The checks are made after a matching instruction was found.  */

static void
warn_if_needed (ins *insn)
{
  /* If the post-increment address mode is used and the load/store
     source register is the same as rbase, the result of the
     instruction is undefined.  */
  if (IS_INSN_TYPE (LD_STOR_INS_INC))
    {
      /* Enough to verify that one of the arguments is a simple reg.  */
      if ((insn->arg[0].type == arg_r) || (insn->arg[1].type == arg_r))
	if (insn->arg[0].r == insn->arg[1].r)
	  as_bad (_("Same src/dest register is used (`r%d'), "
		    "result is undefined"), insn->arg[0].r);
    }

  if (IS_INSN_MNEMONIC ("pop")
      || IS_INSN_MNEMONIC ("push")
      || IS_INSN_MNEMONIC ("popret"))
    {
      unsigned int count = insn->arg[0].constant, reg_val;

      /* Check if count operand caused to save/retrieve the RA twice
	 to generate warning message.  */
      if (insn->nargs > 2)
	{
	  reg_val = getreg_image (insn->arg[1].r);

	  if (   ((reg_val == 9) &&  (count > 7))
		 || ((reg_val == 10) && (count > 6))
		 || ((reg_val == 11) && (count > 5))
		 || ((reg_val == 12) && (count > 4))
		 || ((reg_val == 13) && (count > 2))
		 || ((reg_val == 14) && (count > 0)))
	    as_warn (_("RA register is saved twice."));

	  /* Check if the third operand is "RA" or "ra" */
	  if (!(((insn->arg[2].r) == ra) || ((insn->arg[2].r) == RA)))
	    as_bad (_("`%s' Illegal use of registers."), ins_parse);
	}

      if (insn->nargs > 1)
	{
	  reg_val = getreg_image (insn->arg[1].r);

	  /* If register is a register pair ie r12/r13/r14 in operand1, then
	     the count constant should be validated.  */
	  if (((reg_val == 11) && (count > 7))
	      || ((reg_val == 12) && (count > 6))
	      || ((reg_val == 13) && (count > 4))
	      || ((reg_val == 14) && (count > 2))
	      || ((reg_val == 15) && (count > 0)))
	    as_bad (_("`%s' Illegal count-register combination."), ins_parse);
	}
      else
	{
	  /* Check if the operand is "RA" or "ra" */
	  if (!(((insn->arg[0].r) == ra) || ((insn->arg[0].r) == RA)))
	    as_bad (_("`%s' Illegal use of register."), ins_parse);
	}
    }

  /* Some instruction assume the stack pointer as rptr operand.
     Issue an error when the register to be loaded is also SP.  */
  if (instruction->flags & NO_SP)
    {
      if (getreg_image (insn->arg[1].r) == getreg_image (sp))
	as_bad (_("`%s' has undefined result"), ins_parse);
    }

  /* If the rptr register is specified as one of the registers to be loaded,
     the final contents of rptr are undefined. Thus, we issue an error.  */
  if (instruction->flags & NO_RPTR)
    {
      if ((1 << getreg_image (insn->arg[0].r)) & insn->arg[1].constant)
	as_bad (_("Same src/dest register is used (`r%d'),result is undefined"),
		getreg_image (insn->arg[0].r));
    }
}

/* In some cases, we need to adjust the instruction pointer although a
   match was already found. Here, we gather all these cases.
   Returns 1 if instruction pointer was adjusted, otherwise 0.  */

static int
adjust_if_needed (ins *insn ATTRIBUTE_UNUSED)
{
  int ret_value = 0;

  if ((IS_INSN_TYPE (CSTBIT_INS)) || (IS_INSN_TYPE (LD_STOR_INS)))
    {
      if ((instruction->operands[0].op_type == abs24)
	  && ((insn->arg[0].constant) > 0xF00000))
	{
	  insn->arg[0].constant &= 0xFFFFF;
	  instruction--;
	  ret_value = 1;
	}
    }

  return ret_value;
}

/* Assemble a single instruction:
   INSN is already parsed (that is, all operand values and types are set).
   For instruction to be assembled, we need to find an appropriate template in
   the instruction table, meeting the following conditions:
    1: Has the same number of operands.
    2: Has the same operand types.
    3: Each operand size is sufficient to represent the instruction's values.
   Returns 1 upon success, 0 upon failure.  */

static int
assemble_insn (const char *mnemonic, ins *insn)
{
  /* Type of each operand in the current template.  */
  argtype cur_type[MAX_OPERANDS];
  /* Size (in bits) of each operand in the current template.  */
  unsigned int cur_size[MAX_OPERANDS];
  /* Flags of each operand in the current template.  */
  unsigned int cur_flags[MAX_OPERANDS];
  /* Instruction type to match.  */
  unsigned int ins_type;
  /* Boolean flag to mark whether a match was found.  */
  int match = 0;
  int i;
  /* Nonzero if an instruction with same number of operands was found.  */
  int found_same_number_of_operands = 0;
  /* Nonzero if an instruction with same argument types was found.  */
  int found_same_argument_types = 0;
  /* Nonzero if a constant was found within the required range.  */
  int found_const_within_range  = 0;
  /* Argument number of an operand with invalid type.  */
  int invalid_optype = -1;
  /* Argument number of an operand with invalid constant value.  */
  int invalid_const  = -1;
  /* Operand error (used for issuing various constant error messages).  */
  op_err op_error, const_err = OP_LEGAL;

  /* Retrieve data (based on FUNC) for each operand of a given instruction.  */
#define GET_CURRENT_DATA(FUNC, ARRAY)			\
  for (i = 0; i < insn->nargs; i++)			\
    ARRAY[i] = FUNC (instruction->operands[i].op_type)

#define GET_CURRENT_TYPE    GET_CURRENT_DATA (get_optype, cur_type)
#define GET_CURRENT_SIZE    GET_CURRENT_DATA (get_opbits, cur_size)
#define GET_CURRENT_FLAGS   GET_CURRENT_DATA (get_opflags, cur_flags)

  /* Instruction has no operands -> only copy the constant opcode.   */
  if (insn->nargs == 0)
    {
      output_opcode[0] = BIN (instruction->match, instruction->match_bits);
      return 1;
    }

  /* In some case, same mnemonic can appear with different instruction types.
     For example, 'storb' is supported with 3 different types :
     LD_STOR_INS, LD_STOR_INS_INC, STOR_IMM_INS.
     We assume that when reaching this point, the instruction type was
     pre-determined. We need to make sure that the type stays the same
     during a search for matching instruction.  */
  ins_type = CR16_INS_TYPE (instruction->flags);

  while (/* Check that match is still not found.  */
	 match != 1
	 /* Check we didn't get to end of table.  */
	 && instruction->mnemonic != NULL
	 /* Check that the actual mnemonic is still available.  */
	 && IS_INSN_MNEMONIC (mnemonic)
	 /* Check that the instruction type wasn't changed.  */
	 && IS_INSN_TYPE (ins_type))
    {
      /* Check whether number of arguments is legal.  */
      if (get_number_of_operands () != insn->nargs)
	goto next_insn;
      found_same_number_of_operands = 1;

      /* Initialize arrays with data of each operand in current template.  */
      GET_CURRENT_TYPE;
      GET_CURRENT_SIZE;
      GET_CURRENT_FLAGS;

      /* Check for type compatibility.  */
      for (i = 0; i < insn->nargs; i++)
	{
	  if (cur_type[i] != insn->arg[i].type)
	    {
	      if (invalid_optype == -1)
		invalid_optype = i + 1;
	      goto next_insn;
	    }
	}
      found_same_argument_types = 1;

      for (i = 0; i < insn->nargs; i++)
	{
	  /* If 'bal' instruction size is '2' and reg operand is not 'ra'
	     then goto next instruction.  */
	  if (IS_INSN_MNEMONIC ("bal") && (i == 0)
	      && (instruction->size == 2) && (insn->arg[i].rp != 14))
	    goto next_insn;

	  /* If 'storb' instruction with 'sp' reg and 16-bit disp of
	   * reg-pair, leads to undefined trap, so this should use
	   * 20-bit disp of reg-pair.  */
	  if (IS_INSN_MNEMONIC ("storb") && (instruction->size == 2)
	      && (insn->arg[i].r == 15) && (insn->arg[i + 1].type == arg_crp))
	    goto next_insn;

	  /* Only check range - don't update the constant's value, since the
	     current instruction may not be the last we try to match.
	     The constant's value will be updated later, right before printing
	     it to the object file.  */
	  if ((insn->arg[i].X_op == O_constant)
	      && (op_error = check_range (&insn->arg[i].constant, cur_size[i],
					  cur_flags[i], 0)))
	    {
	      if (invalid_const == -1)
		{
		  invalid_const = i + 1;
		  const_err = op_error;
		}
	      goto next_insn;
	    }
	  /* For symbols, we make sure the relocation size (which was already
	     determined) is sufficient.  */
	  else if ((insn->arg[i].X_op == O_symbol)
		   && ((bfd_reloc_type_lookup (stdoutput, insn->rtype))->bitsize
		       > cur_size[i]))
	    goto next_insn;
	}
      found_const_within_range = 1;

      /* If we got till here -> Full match is found.  */
      match = 1;
      break;

      /* Try again with next instruction.  */
    next_insn:
      instruction++;
    }

  if (!match)
    {
      /* We haven't found a match - instruction can't be assembled.  */
      if (!found_same_number_of_operands)
	as_bad (_("Incorrect number of operands"));
      else if (!found_same_argument_types)
	as_bad (_("Illegal type of operand (arg %d)"), invalid_optype);
      else if (!found_const_within_range)
	{
	  switch (const_err)
	    {
	    case OP_OUT_OF_RANGE:
	      as_bad (_("Operand out of range (arg %d)"), invalid_const);
	      break;
	    case OP_NOT_EVEN:
	      as_bad (_("Operand has odd displacement (arg %d)"), invalid_const);
	      break;
	    default:
	      as_bad (_("Illegal operand (arg %d)"), invalid_const);
	      break;
	    }
	}

      return 0;
    }
  else
    /* Full match - print the encoding to output file.  */
    {
      /* Make further checking (such that couldn't be made earlier).
	 Warn the user if necessary.  */
      warn_if_needed (insn);

      /* Check whether we need to adjust the instruction pointer.  */
      if (adjust_if_needed (insn))
	/* If instruction pointer was adjusted, we need to update
	   the size of the current template operands.  */
	GET_CURRENT_SIZE;

      for (i = 0; i < insn->nargs; i++)
	{
	  int j = instruction->flags & REVERSE_MATCH ?
	    i == 0 ? 1 :
	    i == 1 ? 0 : i :
	    i;

	  /* This time, update constant value before printing it.  */
	  if ((insn->arg[j].X_op == O_constant)
	      && (check_range (&insn->arg[j].constant, cur_size[j],
			       cur_flags[j], 1) != OP_LEGAL))
	    as_fatal (_("Illegal operand (arg %d)"), j+1);
	}

      /* First, copy the instruction's opcode.  */
      output_opcode[0] = BIN (instruction->match, instruction->match_bits);

      for (i = 0; i < insn->nargs; i++)
	{
	  /* For BAL (ra),disp17 instruction only. And also set the
	     DISP24a relocation type.  */
	  if (IS_INSN_MNEMONIC ("bal") && (instruction->size == 2) && i == 0)
	    {
	      insn->rtype = BFD_RELOC_CR16_DISP24a;
	      continue;
	    }
	  cur_arg_num = i;
	  print_operand (cur_size[i], instruction->operands[i].shift,
			 &insn->arg[i]);
	}
    }

  return 1;
}

/* Print the instruction.
   Handle also cases where the instruction is relaxable/relocatable.  */

static void
print_insn (ins *insn)
{
  unsigned int i, j, insn_size;
  char *this_frag;
  unsigned short words[4];
  int addr_mod;

  /* Arrange the insn encodings in a WORD size array.  */
  for (i = 0, j = 0; i < 2; i++)
    {
      words[j++] = (output_opcode[i] >> 16) & 0xFFFF;
      words[j++] = output_opcode[i] & 0xFFFF;
    }

  /* Handle relocation.  */
  if ((instruction->flags & RELAXABLE) && relocatable)
    {
      int relax_subtype;
      /* Write the maximal instruction size supported.  */
      insn_size = INSN_MAX_SIZE;

      if (IS_INSN_TYPE (BRANCH_INS))
	{
	  switch (insn->rtype)
	    {
	    case BFD_RELOC_CR16_DISP24:
	      relax_subtype = 2;
	      break;
	    case BFD_RELOC_CR16_DISP16:
	      relax_subtype = 1;
	      break;
	    default:
	      relax_subtype = 0;
	      break;
	    }
	}
      else
	abort ();

      this_frag = frag_var (rs_machine_dependent, insn_size *2,
			    4, relax_subtype,
			    insn->exp.X_add_symbol,
			    0,
			    0);
    }
  else
    {
      insn_size = instruction->size;
      this_frag = frag_more (insn_size * 2);

      if ((relocatable) && (insn->rtype != BFD_RELOC_NONE))
	{
	  reloc_howto_type *reloc_howto;
	  int size;

	  reloc_howto = bfd_reloc_type_lookup (stdoutput, insn->rtype);

	  if (!reloc_howto)
	    abort ();

	  size = bfd_get_reloc_size (reloc_howto);

	  if (size < 1 || size > 4)
	    abort ();

	  fix_new_exp (frag_now, this_frag - frag_now->fr_literal,
		       size, &insn->exp, reloc_howto->pc_relative,
		       insn->rtype);
	}
    }

  /* Verify a 2-byte code alignment.  */
  addr_mod = frag_now_fix () & 1;
  if (frag_now->has_code && frag_now->insn_addr != addr_mod)
    as_bad (_("instruction address is not a multiple of 2"));
  frag_now->insn_addr = addr_mod;
  frag_now->has_code = 1;

  /* Write the instruction encoding to frag.  */
  for (i = 0; i < insn_size; i++)
    {
      md_number_to_chars (this_frag, (valueT) words[i], 2);
      this_frag += 2;
    }
}

/* Actually assemble an instruction.  */

static void
cr16_assemble (const char *op, char *param)
{
  ins cr16_ins;

  /* Find the instruction.  */
  instruction = (const inst *) str_hash_find (cr16_inst_hash, op);
  if (instruction == NULL)
    {
      as_bad (_("Unknown opcode: `%s'"), op);
      return;
    }

  /* Tie dwarf2 debug info to the address at the start of the insn.  */
  dwarf2_emit_insn (0);

  /* Parse the instruction's operands.  */
  parse_insn (&cr16_ins, param);

  /* Assemble the instruction - return upon failure.  */
  if (assemble_insn (op, &cr16_ins) == 0)
    return;

  /* Print the instruction.  */
  print_insn (&cr16_ins);
}

/* This is the guts of the machine-dependent assembler.  OP points to a
   machine dependent instruction.  This function is supposed to emit
   the frags/bytes it assembles to.  */

void
md_assemble (char *op)
{
  ins cr16_ins;
  char *param, param1[32];

  /* Reset global variables for a new instruction.  */
  reset_vars (op);

  /* Strip the mnemonic.  */
  for (param = op; *param != 0 && !ISSPACE (*param); param++)
    ;
  *param++ = '\0';

  /* bCC instructions and adjust the mnemonic by adding extra white spaces.  */
  if (is_bcc_insn (op))
    {
      strcpy (param1, get_b_cc (op));
      strcat (param1,",");
      strcat (param1, param);
      param = (char *) &param1;
      cr16_assemble ("b", param);
      return;
    }

  /* Checking the cinv options and adjust the mnemonic by removing the
     extra white spaces.  */
  if (streq ("cinv", op))
    {
      /* Validate the cinv options.  */
      unsigned int op_len, param_len;
      check_cinv_options (param);
      op_len = strlen (op);
      param_len = strlen (param) + 1;
      memmove (op + op_len, param, param_len);
    }

  /* MAPPING - SHIFT INSN, if imm4/imm16 positive values
     lsh[b/w] imm4/imm6, reg ==> ashu[b/w] imm4/imm16, reg
     as CR16 core doesn't support lsh[b/w] right shift operations.  */
  if ((streq ("lshb", op) || streq ("lshw", op) || streq ("lshd", op))
      && (param [0] == '$'))
    {
      strcpy (param1, param);
      /* Find the instruction.  */
      instruction = (const inst *) str_hash_find (cr16_inst_hash, op);
      parse_operands (&cr16_ins, param1);
      if (((&cr16_ins)->arg[0].type == arg_ic)
	  && ((&cr16_ins)->arg[0].constant >= 0))
	{
	  if (streq ("lshb", op))
	    cr16_assemble ("ashub", param);
	  else if (streq ("lshd", op))
	    cr16_assemble ("ashud", param);
	  else
	    cr16_assemble ("ashuw", param);
	  return;
	}
    }

  cr16_assemble (op, param);
}
