/* Target definitions for the MorphoRISC1
   Copyright (C) 2005 Free Software Foundation, Inc.
   Contributed by Red Hat, Inc.

   This file is part of GCC.

   GCC 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.

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

#include "config.h"
#include "system.h"
#include "coretypes.h"
#include "tm.h"
#include "rtl.h"
#include "regs.h"
#include "hard-reg-set.h"
#include "real.h"
#include "insn-config.h"
#include "conditions.h"
#include "insn-attr.h"
#include "recog.h"
#include "toplev.h"
#include "output.h"
#include "integrate.h"
#include "tree.h"
#include "function.h"
#include "expr.h"
#include "optabs.h"
#include "libfuncs.h"
#include "flags.h"
#include "tm_p.h"
#include "ggc.h"
#include "insn-flags.h"
#include "obstack.h"
#include "except.h"
#include "target.h"
#include "target-def.h"
#include "basic-block.h"

/* Frame pointer register mask.  */
#define FP_MASK		 	 (1 << (GPR_FP))

/* Link register mask.  */
#define LINK_MASK	 	 (1 << (GPR_LINK))

/* Given a SIZE in bytes, advance to the next word.  */
#define ROUND_ADVANCE(SIZE) (((SIZE) + UNITS_PER_WORD - 1) / UNITS_PER_WORD)

/* A C structure for machine-specific, per-function data.
   This is added to the cfun structure.  */
struct machine_function GTY(())
{
  /* Flags if __builtin_return_address (n) with n >= 1 was used.  */
  int ra_needs_full_frame;
  struct rtx_def * eh_stack_adjust;
  int interrupt_handler;
  int has_loops;
};

/* Define the information needed to generate branch and scc insns.
   This is stored from the compare operation.  */
struct rtx_def * mt_compare_op0;
struct rtx_def * mt_compare_op1;

/* Current frame information calculated by compute_frame_size.  */
struct mt_frame_info current_frame_info;

/* Zero structure to initialize current_frame_info.  */
struct mt_frame_info zero_frame_info;

/* mt doesn't have unsigned compares need a library call for this.  */
struct rtx_def * mt_ucmpsi3_libcall;

static int mt_flag_delayed_branch;


static rtx
mt_struct_value_rtx (tree fndecl ATTRIBUTE_UNUSED,
			 int incoming ATTRIBUTE_UNUSED)
{
  return gen_rtx_REG (Pmode, RETVAL_REGNUM);
}

/* Implement RETURN_ADDR_RTX.  */
rtx
mt_return_addr_rtx (int count)
{
  if (count != 0)
    return NULL_RTX;

  return get_hard_reg_initial_val (Pmode, GPR_LINK);
}

/* The following variable value indicates the number of nops required
   between the current instruction and the next instruction to avoid
   any pipeline hazards.  */
static int mt_nops_required = 0;
static const char * mt_nop_reasons = "";

/* Implement ASM_OUTPUT_OPCODE.  */
const char *
mt_asm_output_opcode (FILE *f ATTRIBUTE_UNUSED, const char *ptr)
{
  if (mt_nops_required)
    fprintf (f, ";# need %d nops because of %s\n\t",
	     mt_nops_required, mt_nop_reasons);
  
  while (mt_nops_required)
    {
      fprintf (f, "nop\n\t");
      -- mt_nops_required;
    }
  
  return ptr;
}

/* Given an insn, return whether it's a memory operation or a branch
   operation, otherwise return TYPE_ARITH.  */
static enum attr_type
mt_get_attr_type (rtx complete_insn)
{
  rtx insn = PATTERN (complete_insn);

  if (JUMP_P (complete_insn))
    return TYPE_BRANCH;
  if (CALL_P (complete_insn))
    return TYPE_BRANCH;

  if (GET_CODE (insn) != SET)
    return TYPE_ARITH;

  if (SET_DEST (insn) == pc_rtx)
    return TYPE_BRANCH;

  if (GET_CODE (SET_DEST (insn)) == MEM)
    return TYPE_STORE;

  if (GET_CODE (SET_SRC (insn)) == MEM)
    return TYPE_LOAD;
  
  return TYPE_ARITH;
}

/* A helper routine for insn_dependent_p called through note_stores.  */

static void
insn_dependent_p_1 (rtx x, rtx pat ATTRIBUTE_UNUSED, void *data)
{
  rtx * pinsn = (rtx *) data;

  if (*pinsn && reg_mentioned_p (x, *pinsn))
    *pinsn = NULL_RTX;
}

/* Return true if anything in insn X is (anti,output,true)
   dependent on anything in insn Y.  */

static bool
insn_dependent_p (rtx x, rtx y)
{
  rtx tmp;

  if (! INSN_P (x) || ! INSN_P (y))
    return 0;

  tmp = PATTERN (y);
  note_stores (PATTERN (x), insn_dependent_p_1, &tmp);
  if (tmp == NULL_RTX)
    return true;

  tmp = PATTERN (x);
  note_stores (PATTERN (y), insn_dependent_p_1, &tmp);
  return (tmp == NULL_RTX);
}


/* Return true if anything in insn X is true dependent on anything in
   insn Y.  */
static bool
insn_true_dependent_p (rtx x, rtx y)
{
  rtx tmp;

  if (! INSN_P (x) || ! INSN_P (y))
    return 0;

  tmp = PATTERN (y);
  note_stores (PATTERN (x), insn_dependent_p_1, &tmp);
  return (tmp == NULL_RTX);
}

/* The following determines the number of nops that need to be
   inserted between the previous instructions and current instruction
   to avoid pipeline hazards on the mt processor.  Remember that
   the function is not called for asm insns.  */

void
mt_final_prescan_insn (rtx   insn,
			rtx * opvec ATTRIBUTE_UNUSED,
			int   noperands ATTRIBUTE_UNUSED)
{
  rtx prev_i;
  enum attr_type prev_attr;

  mt_nops_required = 0;
  mt_nop_reasons = "";

  /* ms2 constraints are dealt with in reorg.  */
  if (TARGET_MS2)
    return;
  
  /* Only worry about real instructions.  */
  if (! INSN_P (insn))
    return;

  /* Find the previous real instructions.  */
  for (prev_i = PREV_INSN (insn);
       prev_i != NULL
	 && (! INSN_P (prev_i)
	     || GET_CODE (PATTERN (prev_i)) == USE
	     || GET_CODE (PATTERN (prev_i)) == CLOBBER);
       prev_i = PREV_INSN (prev_i))
    {
      /* If we meet a barrier, there is no flow through here.  */
      if (BARRIER_P (prev_i))
	return;
    }
  
  /* If there isn't one then there is nothing that we need do.  */
  if (prev_i == NULL || ! INSN_P (prev_i))
    return;

  prev_attr = mt_get_attr_type (prev_i);
  
  /* Delayed branch slots already taken care of by delay branch scheduling.  */
  if (prev_attr == TYPE_BRANCH)
    return;

  switch (mt_get_attr_type (insn))
    {
    case TYPE_LOAD:
    case TYPE_STORE:
      /* Avoid consecutive memory operation.  */
      if  ((prev_attr == TYPE_LOAD || prev_attr == TYPE_STORE)
	   && TARGET_MS1_64_001)
	{
	  mt_nops_required = 1;
	  mt_nop_reasons = "consecutive mem ops";
	}
      /* Drop through.  */

    case TYPE_ARITH:
    case TYPE_COMPLEX:
      /* One cycle of delay is required between load
	 and the dependent arithmetic instruction.  */
      if (prev_attr == TYPE_LOAD
	  && insn_true_dependent_p (prev_i, insn))
	{
	  mt_nops_required = 1;
	  mt_nop_reasons = "load->arith dependency delay";
	}
      break;

    case TYPE_BRANCH:
      if (insn_dependent_p (prev_i, insn))
	{
	  if (prev_attr == TYPE_ARITH && TARGET_MS1_64_001)
	    {
	      /* One cycle of delay between arith
		 instructions and branch dependent on arith.  */
	      mt_nops_required = 1;
	      mt_nop_reasons = "arith->branch dependency delay";
	    }
	  else if (prev_attr == TYPE_LOAD)
	    {
	      /* Two cycles of delay are required
		 between load and dependent branch.  */
	      if (TARGET_MS1_64_001)
		mt_nops_required = 2;
	      else
		mt_nops_required = 1;
	      mt_nop_reasons = "load->branch dependency delay";
	    }
	}
      break;

    default:
      fatal_insn ("mt_final_prescan_insn, invalid insn #1", insn);
      break;
    }
}

/* Print debugging information for a frame.  */
static void
mt_debug_stack (struct mt_frame_info * info)
{
  int regno;

  if (!info)
    {
      error ("info pointer NULL");
      gcc_unreachable ();
    }

  fprintf (stderr, "\nStack information for function %s:\n",
	   ((current_function_decl && DECL_NAME (current_function_decl))
	    ? IDENTIFIER_POINTER (DECL_NAME (current_function_decl))
	    : "<unknown>"));

  fprintf (stderr, "\ttotal_size       = %d\n", info->total_size);
  fprintf (stderr, "\tpretend_size     = %d\n", info->pretend_size);
  fprintf (stderr, "\targs_size        = %d\n", info->args_size);
  fprintf (stderr, "\textra_size       = %d\n", info->extra_size);
  fprintf (stderr, "\treg_size         = %d\n", info->reg_size);
  fprintf (stderr, "\tvar_size         = %d\n", info->var_size);
  fprintf (stderr, "\tframe_size       = %d\n", info->frame_size);
  fprintf (stderr, "\treg_mask         = 0x%x\n", info->reg_mask);
  fprintf (stderr, "\tsave_fp          = %d\n", info->save_fp);
  fprintf (stderr, "\tsave_lr          = %d\n", info->save_lr);
  fprintf (stderr, "\tinitialized      = %d\n", info->initialized);
  fprintf (stderr, "\tsaved registers =");

  /* Print out reg_mask in a more readable format.  */
  for (regno = GPR_R0; regno <= GPR_LAST; regno++)
    if ( (1 << regno) & info->reg_mask)
      fprintf (stderr, " %s", reg_names[regno]);

  putc ('\n', stderr);
  fflush (stderr);
}

/* Print a memory address as an operand to reference that memory location.  */

static void
mt_print_operand_simple_address (FILE * file, rtx addr)
{
  if (!addr)
    error ("PRINT_OPERAND_ADDRESS, null pointer");

  else
    switch (GET_CODE (addr))
      {
      case REG:
	fprintf (file, "%s, #0", reg_names [REGNO (addr)]);
	break;
	
      case PLUS:
	{
	  rtx reg = 0;
	  rtx offset = 0;
	  rtx arg0 = XEXP (addr, 0);
	  rtx arg1 = XEXP (addr, 1);

	  if (GET_CODE (arg0) == REG)
	    {
	      reg = arg0;
	      offset = arg1;
	      if (GET_CODE (offset) == REG)
		fatal_insn ("PRINT_OPERAND_ADDRESS, 2 regs", addr);
	    }

	  else if (GET_CODE (arg1) == REG)
	      reg = arg1, offset = arg0;
	  else if (CONSTANT_P (arg0) && CONSTANT_P (arg1))
	    {
	      fprintf (file, "%s, #", reg_names [GPR_R0]);
	      output_addr_const (file, addr);
	      break;
	    }
	  fprintf (file, "%s, #", reg_names [REGNO (reg)]);
	  output_addr_const (file, offset);
	  break;
	}

      case LABEL_REF:
      case SYMBOL_REF:
      case CONST_INT:
      case CONST:
	output_addr_const (file, addr);
	break;

      default:
	fatal_insn ("PRINT_OPERAND_ADDRESS, invalid insn #1", addr);
	break;
      }
}

/* Implement PRINT_OPERAND_ADDRESS.  */
void
mt_print_operand_address (FILE * file, rtx addr)
{
  if (GET_CODE (addr) == AND
      && GET_CODE (XEXP (addr, 1)) == CONST_INT
      && INTVAL (XEXP (addr, 1)) == -3)
    mt_print_operand_simple_address (file, XEXP (addr, 0));
  else
    mt_print_operand_simple_address (file, addr);
}

/* Implement PRINT_OPERAND.  */
void
mt_print_operand (FILE * file, rtx x, int code)
{
  switch (code)
    {
    case '#':
      /* Output a nop if there's nothing for the delay slot.  */
      if (dbr_sequence_length () == 0)
	fputs ("\n\tnop", file);
      return;
      
    case 'H': 
      fprintf(file, "#%%hi16(");
      output_addr_const (file, x);
      fprintf(file, ")");
      return;
      
    case 'L': 
      fprintf(file, "#%%lo16(");
      output_addr_const (file, x);
      fprintf(file, ")");
      return;

    case 'N': 
      fprintf(file, "#%ld", ~INTVAL (x));
      return;

    case 'z':
      if (GET_CODE (x) == CONST_INT && INTVAL (x) == 0)
	{
	  fputs (reg_names[GPR_R0], file);
	  return;
	}

    case 0:
      /* Handled below.  */
      break;

    default:
      /* output_operand_lossage ("mt_print_operand: unknown code"); */
      fprintf (file, "unknown code");
      return;
    }

  switch (GET_CODE (x))
    {
    case REG:
      fputs (reg_names [REGNO (x)], file);
      break;

    case CONST:
    case CONST_INT:
      fprintf(file, "#%ld", INTVAL (x));
      break;

    case MEM:
      mt_print_operand_address(file, XEXP (x,0));
      break;

    case LABEL_REF:
    case SYMBOL_REF:
      output_addr_const (file, x);
      break;
      
    default:
      fprintf(file, "Uknown code: %d", GET_CODE (x));
      break;
    }

  return;
}

/* Implement INIT_CUMULATIVE_ARGS.  */
void
mt_init_cumulative_args (CUMULATIVE_ARGS * cum, tree fntype, rtx libname,
			 tree fndecl ATTRIBUTE_UNUSED, int incoming)
{
  *cum = 0;

  if (TARGET_DEBUG_ARG)
    {
      fprintf (stderr, "\nmt_init_cumulative_args:");

      if (incoming)
	fputs (" incoming", stderr);

      if (fntype)
	{
	  tree ret_type = TREE_TYPE (fntype);
	  fprintf (stderr, " return = %s,",
		   tree_code_name[ (int)TREE_CODE (ret_type) ]);
	}

      if (libname && GET_CODE (libname) == SYMBOL_REF)
	fprintf (stderr, " libname = %s", XSTR (libname, 0));

      if (cfun->returns_struct)
	fprintf (stderr, " return-struct");

      putc ('\n', stderr);
    }
}

/* Compute the slot number to pass an argument in.
   Returns the slot number or -1 if passing on the stack.

   CUM is a variable of type CUMULATIVE_ARGS which gives info about
    the preceding args and about the function being called.
   MODE is the argument's machine mode.
   TYPE is the data type of the argument (as a tree).
    This is null for libcalls where that information may
    not be available.
   NAMED is nonzero if this argument is a named parameter
    (otherwise it is an extra parameter matching an ellipsis).
   INCOMING_P is zero for FUNCTION_ARG, nonzero for FUNCTION_INCOMING_ARG.
   *PREGNO records the register number to use if scalar type.  */

static int
mt_function_arg_slotno (const CUMULATIVE_ARGS * cum,
			enum machine_mode mode,
			tree type,
			int named ATTRIBUTE_UNUSED,
			int incoming_p ATTRIBUTE_UNUSED,
			int * pregno)
{
  int regbase = FIRST_ARG_REGNUM;
  int slotno  = * cum;

  if (mode == VOIDmode || targetm.calls.must_pass_in_stack (mode, type))
    return -1;

  if (slotno >= MT_NUM_ARG_REGS)
    return -1;

  * pregno = regbase + slotno;

  return slotno;
}

/* Implement FUNCTION_ARG.  */
rtx
mt_function_arg (const CUMULATIVE_ARGS * cum,
		 enum machine_mode mode,
		 tree type,
		 int named,
		 int incoming_p)
{
  int slotno, regno;
  rtx reg;

  slotno = mt_function_arg_slotno (cum, mode, type, named, incoming_p, &regno);

  if (slotno == -1)
    reg = NULL_RTX;
  else
    reg = gen_rtx_REG (mode, regno);

  return reg;
}

/* Implement FUNCTION_ARG_ADVANCE.  */
void
mt_function_arg_advance (CUMULATIVE_ARGS * cum,
			 enum machine_mode mode,
			 tree type ATTRIBUTE_UNUSED,
			 int named)
{
  int slotno, regno;

  /* We pass 0 for incoming_p here, it doesn't matter.  */
  slotno = mt_function_arg_slotno (cum, mode, type, named, 0, &regno);

  * cum += (mode != BLKmode
	    ? ROUND_ADVANCE (GET_MODE_SIZE (mode))
	    : ROUND_ADVANCE (int_size_in_bytes (type)));

  if (TARGET_DEBUG_ARG)
    fprintf (stderr,
	     "mt_function_arg_advance: words = %2d, mode = %4s, named = %d, size = %3d\n",
	     *cum, GET_MODE_NAME (mode), named, 
	     (*cum) * UNITS_PER_WORD);
}

/* Implement hook TARGET_ARG_PARTIAL_BYTES.

   Returns the number of bytes at the beginning of an argument that
   must be put in registers.  The value must be zero for arguments
   that are passed entirely in registers or that are entirely pushed
   on the stack.  */
static int
mt_arg_partial_bytes (CUMULATIVE_ARGS * pcum,
		       enum machine_mode mode,
		       tree type,
		       bool named ATTRIBUTE_UNUSED)
{
  int cum = * pcum;
  int words;

  if (mode == BLKmode)
    words = ((int_size_in_bytes (type) + UNITS_PER_WORD - 1)
	     / UNITS_PER_WORD);
  else
    words = (GET_MODE_SIZE (mode) + UNITS_PER_WORD - 1) / UNITS_PER_WORD;

  if (! targetm.calls.pass_by_reference (&cum, mode, type, named)
      && cum < MT_NUM_ARG_REGS
      && (cum + words) > MT_NUM_ARG_REGS)
    {
      int bytes = (MT_NUM_ARG_REGS - cum) * UNITS_PER_WORD; 

      if (TARGET_DEBUG)
	fprintf (stderr, "function_arg_partial_nregs = %d\n", bytes);
      return bytes;
    }

  return 0;
}


/* Implement TARGET_PASS_BY_REFERENCE hook.  */
static bool
mt_pass_by_reference (CUMULATIVE_ARGS * cum ATTRIBUTE_UNUSED,
		       enum machine_mode mode ATTRIBUTE_UNUSED,
		       tree type,
		       bool named ATTRIBUTE_UNUSED)
{
  return (type && int_size_in_bytes (type) > 4 * UNITS_PER_WORD);
}

/* Implement FUNCTION_ARG_BOUNDARY.  */
int
mt_function_arg_boundary (enum machine_mode mode ATTRIBUTE_UNUSED,
			   tree type ATTRIBUTE_UNUSED)
{
  return BITS_PER_WORD;
}

/* Implement REG_OK_FOR_BASE_P.  */
int
mt_reg_ok_for_base_p (rtx x, int strict)
{
  if (strict)
    return  (((unsigned) REGNO (x)) < FIRST_PSEUDO_REGISTER);
  return 1;
}

/* Helper function of mt_legitimate_address_p.  Return true if XINSN
   is a simple address, otherwise false.  */
static bool
mt_legitimate_simple_address_p (enum machine_mode mode ATTRIBUTE_UNUSED,
				rtx xinsn, int strict)
{
  if (TARGET_DEBUG)						
    {									
      fprintf (stderr, "\n========== GO_IF_LEGITIMATE_ADDRESS, %sstrict\n",
	       strict ? "" : "not ");
      debug_rtx (xinsn);
    }

  if (GET_CODE (xinsn) == REG && mt_reg_ok_for_base_p (xinsn, strict))
    return true;

  if (GET_CODE (xinsn) == PLUS
      && GET_CODE (XEXP (xinsn, 0)) == REG
      && mt_reg_ok_for_base_p (XEXP (xinsn, 0), strict)
      && GET_CODE (XEXP (xinsn, 1)) == CONST_INT
      && SMALL_INT (XEXP (xinsn, 1)))
    return true;

  return false;
}


/* Helper function of GO_IF_LEGITIMATE_ADDRESS.  Return nonzero if
   XINSN is a legitimate address on MT.  */
int
mt_legitimate_address_p (enum machine_mode mode, rtx xinsn, int strict)
{
  if (mt_legitimate_simple_address_p (mode, xinsn, strict))
    return 1;

  if ((mode) == SImode
      && GET_CODE (xinsn) == AND
      && GET_CODE (XEXP (xinsn, 1)) == CONST_INT
      && INTVAL (XEXP (xinsn, 1)) == -3)
    return mt_legitimate_simple_address_p (mode, XEXP (xinsn, 0), strict);
  else
    return 0;
}

/* Return truth value of whether OP can be used as an operands where a
   register or 16 bit unsigned integer is needed.  */

int
uns_arith_operand (rtx op, enum machine_mode mode)
{
  if (GET_CODE (op) == CONST_INT && SMALL_INT_UNSIGNED (op))
    return 1;

  return register_operand (op, mode);
}

/* Return truth value of whether OP can be used as an operands where a
   16 bit integer is needed.  */

int
arith_operand (rtx op, enum machine_mode mode)
{
  if (GET_CODE (op) == CONST_INT && SMALL_INT (op))
    return 1;

  return register_operand (op, mode);
}

/* Return truth value of whether OP is a register or the constant 0.  */

int
reg_or_0_operand (rtx op, enum machine_mode mode)
{
  switch (GET_CODE (op))
    {
    case CONST_INT:
      return INTVAL (op) == 0;

    case REG:
    case SUBREG:
      return register_operand (op, mode);

    default:
      break;
    }

  return 0;
}

/* Return truth value of whether OP is a constant that requires two
   loads to put in a register.  */

int
big_const_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED)
{
  if (GET_CODE (op) == CONST_INT && CONST_OK_FOR_LETTER_P (INTVAL (op), 'M'))
    return 1;

  return 0;
}

/* Return truth value of whether OP is a constant that require only
   one load to put in a register.  */

int
single_const_operand (rtx op, enum machine_mode mode ATTRIBUTE_UNUSED)
{
  if (big_const_operand (op, mode)
      || GET_CODE (op) == CONST
      || GET_CODE (op) == LABEL_REF
      || GET_CODE (op) == SYMBOL_REF)
    return 0;

  return 1;
}

/* True if the current function is an interrupt handler
   (either via #pragma or an attribute specification).  */
int interrupt_handler;
enum processor_type mt_cpu;

static struct machine_function *
mt_init_machine_status (void)
{
  struct machine_function *f;

  f = ggc_alloc_cleared (sizeof (struct machine_function));

  return f;
}

/* Implement OVERRIDE_OPTIONS.  */
void
mt_override_options (void)
{
  if (mt_cpu_string != NULL)
    {
      if (!strcmp (mt_cpu_string, "ms1-64-001"))
	mt_cpu = PROCESSOR_MS1_64_001;
      else if (!strcmp (mt_cpu_string, "ms1-16-002"))
	mt_cpu = PROCESSOR_MS1_16_002;
      else if  (!strcmp (mt_cpu_string, "ms1-16-003"))
	mt_cpu = PROCESSOR_MS1_16_003;
      else if (!strcmp (mt_cpu_string, "ms2"))
	mt_cpu = PROCESSOR_MS2;
      else
	error ("bad value (%s) for -march= switch", mt_cpu_string);
    }
  else
    mt_cpu = PROCESSOR_MS1_16_002;

  if (flag_exceptions)
    {
      flag_omit_frame_pointer = 0;
      flag_gcse = 0;
    }

  /* We do delayed branch filling in machine dependent reorg */
  mt_flag_delayed_branch = flag_delayed_branch;
  flag_delayed_branch = 0;

  init_machine_status = mt_init_machine_status;
}

/* Do what is necessary for `va_start'.  We look at the current function
   to determine if stdarg or varargs is used and return the address of the
   first unnamed parameter.  */

static void
mt_setup_incoming_varargs (CUMULATIVE_ARGS *cum,
			   enum machine_mode mode ATTRIBUTE_UNUSED,
			   tree type ATTRIBUTE_UNUSED,
			   int *pretend_size, int no_rtl)
{
  int regno;
  int regs = MT_NUM_ARG_REGS - *cum;
  
  *pretend_size = regs < 0 ? 0 : GET_MODE_SIZE (SImode) * regs;
  
  if (no_rtl)
    return;
  
  for (regno = *cum; regno < MT_NUM_ARG_REGS; regno++)
    {
      rtx reg = gen_rtx_REG (SImode, FIRST_ARG_REGNUM + regno);
      rtx slot = gen_rtx_PLUS (Pmode,
			       gen_rtx_REG (SImode, ARG_POINTER_REGNUM),
			       GEN_INT (UNITS_PER_WORD * regno));
      
      emit_move_insn (gen_rtx_MEM (SImode, slot), reg);
    }
}

/* Returns the number of bytes offset between the frame pointer and the stack
   pointer for the current function.  SIZE is the number of bytes of space
   needed for local variables.  */

unsigned int
mt_compute_frame_size (int size)
{
  int           regno;
  unsigned int  total_size;
  unsigned int  var_size;
  unsigned int  args_size;
  unsigned int  pretend_size;
  unsigned int  extra_size;
  unsigned int  reg_size;
  unsigned int  frame_size;
  unsigned int  reg_mask;

  var_size      = size;
  args_size     = current_function_outgoing_args_size;
  pretend_size  = current_function_pretend_args_size;
  extra_size    = FIRST_PARM_OFFSET (0);
  total_size    = extra_size + pretend_size + args_size + var_size;
  reg_size      = 0;
  reg_mask	= 0;

  /* Calculate space needed for registers.  */
  for (regno = GPR_R0; regno <= GPR_LAST; regno++)
    {
      if (MUST_SAVE_REGISTER (regno))
        {
          reg_size += UNITS_PER_WORD;
          reg_mask |= 1 << regno;
        }
    }

  current_frame_info.save_fp = (regs_ever_live [GPR_FP]
				|| frame_pointer_needed
				|| interrupt_handler);
  current_frame_info.save_lr = (regs_ever_live [GPR_LINK]
				|| profile_flag
				|| interrupt_handler);
 
  reg_size += (current_frame_info.save_fp + current_frame_info.save_lr)
               * UNITS_PER_WORD;
  total_size += reg_size;
  total_size = ((total_size + 3) & ~3);

  frame_size = total_size;

  /* Save computed information.  */
  current_frame_info.pretend_size = pretend_size;
  current_frame_info.var_size     = var_size;
  current_frame_info.args_size    = args_size;
  current_frame_info.reg_size     = reg_size;
  current_frame_info.frame_size   = args_size + var_size;
  current_frame_info.total_size   = total_size;
  current_frame_info.extra_size   = extra_size;
  current_frame_info.reg_mask     = reg_mask;
  current_frame_info.initialized  = reload_completed;
 
  return total_size;
}

/* Emit code to save REG in stack offset pointed to by MEM.
   STACK_OFFSET is the offset from the SP where the save will happen.
   This function sets the REG_FRAME_RELATED_EXPR note accordingly.  */
static void
mt_emit_save_restore (enum save_direction direction,
		      rtx reg, rtx mem, int stack_offset)
{
  if (direction == FROM_PROCESSOR_TO_MEM)
    {
      rtx insn;
  
      insn = emit_move_insn (mem, reg);
      RTX_FRAME_RELATED_P (insn) = 1;
      REG_NOTES (insn)
	= gen_rtx_EXPR_LIST
	(REG_FRAME_RELATED_EXPR,
	 gen_rtx_SET (VOIDmode,
		      gen_rtx_MEM (SImode,
				   gen_rtx_PLUS (SImode,
						 stack_pointer_rtx,
						 GEN_INT (stack_offset))),
		      reg),
	 REG_NOTES (insn));
    }
  else
    emit_move_insn (reg, mem);
}


/* Emit code to save the frame pointer in the prologue and restore
   frame pointer in epilogue.  */

static void
mt_emit_save_fp (enum save_direction direction,
		  struct mt_frame_info info)
{
  rtx base_reg;
  int reg_mask = info.reg_mask  & ~(FP_MASK | LINK_MASK);
  int offset = info.total_size;
  int stack_offset = info.total_size;

  /* If there is nothing to save, get out now.  */
  if (! info.save_fp && ! info.save_lr && ! reg_mask)
    return;

  /* If offset doesn't fit in a 15-bit signed integer,
     uses a scratch registers to get a smaller offset.  */
  if (CONST_OK_FOR_LETTER_P(offset, 'O'))
    base_reg = stack_pointer_rtx;
  else
    {
      /* Use the scratch register R9 that holds old stack pointer.  */
      base_reg = gen_rtx_REG (SImode, GPR_R9);
      offset = 0;
    }

  if (info.save_fp)
    {
      offset -= UNITS_PER_WORD;
      stack_offset -= UNITS_PER_WORD;
      mt_emit_save_restore
	(direction, gen_rtx_REG (SImode, GPR_FP),
	 gen_rtx_MEM (SImode,
		      gen_rtx_PLUS (SImode, base_reg, GEN_INT (offset))),
	 stack_offset);
    }
}

/* Emit code to save registers in the prologue and restore register
   in epilogue.  */

static void
mt_emit_save_regs (enum save_direction direction,
		    struct mt_frame_info info)
{
  rtx base_reg;
  int regno;
  int reg_mask = info.reg_mask  & ~(FP_MASK | LINK_MASK);
  int offset = info.total_size;
  int stack_offset = info.total_size;

  /* If there is nothing to save, get out now.  */
  if (! info.save_fp && ! info.save_lr && ! reg_mask)
    return;

  /* If offset doesn't fit in a 15-bit signed integer,
     uses a scratch registers to get a smaller offset.  */
  if (CONST_OK_FOR_LETTER_P(offset, 'O'))
    base_reg = stack_pointer_rtx;
  else
    {
      /* Use the scratch register R9 that holds old stack pointer.  */
      base_reg = gen_rtx_REG (SImode, GPR_R9);
      offset = 0;
    }

  if (info.save_fp)
    {
      /* This just records the space for it, the actual move generated in
	 mt_emit_save_fp ().  */
      offset -= UNITS_PER_WORD;
      stack_offset -= UNITS_PER_WORD;
    }

  if (info.save_lr)
    {
      offset -= UNITS_PER_WORD;
      stack_offset -= UNITS_PER_WORD;
      mt_emit_save_restore
	(direction, gen_rtx_REG (SImode, GPR_LINK), 
	 gen_rtx_MEM (SImode,
		      gen_rtx_PLUS (SImode, base_reg, GEN_INT (offset))),
	 stack_offset);
    }

  /* Save any needed call-saved regs.  */
  for (regno = GPR_R0; regno <= GPR_LAST; regno++)
    {
      if ((reg_mask & (1 << regno)) != 0)
	{
	  offset -= UNITS_PER_WORD;
	  stack_offset -= UNITS_PER_WORD;
	  mt_emit_save_restore
	    (direction, gen_rtx_REG (SImode, regno),
	     gen_rtx_MEM (SImode,
			  gen_rtx_PLUS (SImode, base_reg, GEN_INT (offset))),
	     stack_offset);
	}
    }
}

/* Return true if FUNC is a function with the 'interrupt' attribute.  */
static bool
mt_interrupt_function_p (tree func)
{
  tree a;

  if (TREE_CODE (func) != FUNCTION_DECL)
    return false;

  a = lookup_attribute ("interrupt", DECL_ATTRIBUTES (func));
  return a != NULL_TREE;
}

/* Generate prologue code.  */
void
mt_expand_prologue (void)
{
  rtx size_rtx, insn;
  unsigned int frame_size;

  if (mt_interrupt_function_p (current_function_decl))
    {
      interrupt_handler = 1;
      if (cfun->machine)
	cfun->machine->interrupt_handler = 1;
    }

  mt_compute_frame_size (get_frame_size ());

  if (TARGET_DEBUG_STACK)
    mt_debug_stack (&current_frame_info);

  /* Compute size of stack adjustment.  */
  frame_size = current_frame_info.total_size;

  /* If offset doesn't fit in a 15-bit signed integer,
     uses a scratch registers to get a smaller offset.  */
  if (CONST_OK_FOR_LETTER_P(frame_size, 'O'))
    size_rtx = GEN_INT (frame_size);
  else
    {
      /* We do not have any scratch registers.  */
      gcc_assert (!interrupt_handler);

      size_rtx = gen_rtx_REG (SImode, GPR_R9);
      insn = emit_move_insn (size_rtx, GEN_INT (frame_size & 0xffff0000));
      insn = emit_insn (gen_iorsi3 (size_rtx, size_rtx,
				    GEN_INT (frame_size & 0x0000ffff)));
    }

  /* Allocate stack for this frame.  */
  /* Make stack adjustment and use scratch register if constant too
     large to fit as immediate.  */
  if (frame_size)
    {
      insn = emit_insn (gen_subsi3 (stack_pointer_rtx,
				 stack_pointer_rtx,
				 size_rtx));
      RTX_FRAME_RELATED_P (insn) = 1;
      REG_NOTES (insn)
	= gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
			     gen_rtx_SET (VOIDmode,
					  stack_pointer_rtx,
					  gen_rtx_MINUS (SImode,
							stack_pointer_rtx,
							GEN_INT (frame_size))),
			     REG_NOTES (insn));
    }

  /* Set R9 to point to old sp if required for access to register save
     area.  */
  if ( current_frame_info.reg_size != 0
       && !CONST_OK_FOR_LETTER_P (frame_size, 'O'))
      emit_insn (gen_addsi3 (size_rtx, size_rtx, stack_pointer_rtx));
  
  /* Save the frame pointer.  */
  mt_emit_save_fp (FROM_PROCESSOR_TO_MEM, current_frame_info);

  /* Now put the frame pointer into the frame pointer register.  */
  if (frame_pointer_needed)
    {
      insn = emit_move_insn (frame_pointer_rtx, stack_pointer_rtx);
      RTX_FRAME_RELATED_P (insn) = 1;
    }

  /* Save the registers.  */
  mt_emit_save_regs (FROM_PROCESSOR_TO_MEM, current_frame_info);

  /* If we are profiling, make sure no instructions are scheduled before
     the call to mcount.  */
  if (profile_flag)
    emit_insn (gen_blockage ());
}

/* Implement EPILOGUE_USES.  */
int
mt_epilogue_uses (int regno)
{
  if (cfun->machine && cfun->machine->interrupt_handler && reload_completed)
    return 1;
  return regno == GPR_LINK;
}

/* Generate epilogue.  EH_MODE is NORMAL_EPILOGUE when generating a
   function epilogue, or EH_EPILOGUE when generating an EH
   epilogue.  */
void
mt_expand_epilogue (enum epilogue_type eh_mode)
{
  rtx size_rtx, insn;
  unsigned frame_size;

  mt_compute_frame_size (get_frame_size ());

  if (TARGET_DEBUG_STACK)
    mt_debug_stack (& current_frame_info);

  /* Compute size of stack adjustment.  */
  frame_size = current_frame_info.total_size;

  /* If offset doesn't fit in a 15-bit signed integer,
     uses a scratch registers to get a smaller offset.  */
  if (CONST_OK_FOR_LETTER_P(frame_size, 'O'))
    size_rtx = GEN_INT (frame_size);
  else
    {
      /* We do not have any scratch registers.  */
      gcc_assert (!interrupt_handler);

      size_rtx = gen_rtx_REG (SImode, GPR_R9);
      insn = emit_move_insn (size_rtx, GEN_INT (frame_size & 0xffff0000));
      insn = emit_insn (gen_iorsi3 (size_rtx, size_rtx,
				    GEN_INT (frame_size & 0x0000ffff)));
      /* Set R9 to point to old sp if required for access to register
	 save area.  */
      emit_insn (gen_addsi3 (size_rtx, size_rtx, stack_pointer_rtx));
    }

  /* Restore sp if there was some possible change to it.  */
  if (frame_pointer_needed)
    insn = emit_move_insn (stack_pointer_rtx, frame_pointer_rtx);

  /* Restore the registers.  */
  mt_emit_save_fp (FROM_MEM_TO_PROCESSOR, current_frame_info);
  mt_emit_save_regs (FROM_MEM_TO_PROCESSOR, current_frame_info);

  /* Make stack adjustment and use scratch register if constant too
     large to fit as immediate.  */
  if (frame_size)
    {
      if (CONST_OK_FOR_LETTER_P(frame_size, 'O'))
	/* Can handle this with simple add.  */
	insn = emit_insn (gen_addsi3 (stack_pointer_rtx,
				      stack_pointer_rtx,
				      size_rtx));
      else
	/* Scratch reg R9 has the old sp value.  */
	insn = emit_move_insn (stack_pointer_rtx, 
			       gen_rtx_REG (SImode, GPR_R9));

      REG_NOTES (insn)
	= gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
			     gen_rtx_SET (VOIDmode,
					  stack_pointer_rtx,
					  gen_rtx_PLUS (SImode,
							stack_pointer_rtx,
							GEN_INT (frame_size))),
			     REG_NOTES (insn));
    }

  if (cfun->machine && cfun->machine->eh_stack_adjust != NULL_RTX)
    /* Perform the additional bump for __throw.  */
    emit_insn (gen_addsi3 (stack_pointer_rtx,
			   stack_pointer_rtx,
			   cfun->machine->eh_stack_adjust));

  /* Generate the appropriate return.  */
  if (eh_mode == EH_EPILOGUE)
    {
      emit_jump_insn (gen_eh_return_internal ());
      emit_barrier ();
    }
  else if (interrupt_handler)
    emit_jump_insn (gen_return_interrupt_internal ());
  else
    emit_jump_insn (gen_return_internal ());

  /* Reset state info for each function.  */
  interrupt_handler = 0;
  current_frame_info = zero_frame_info;
  if (cfun->machine)
    cfun->machine->eh_stack_adjust = NULL_RTX;
}


/* Generate code for the "eh_return" pattern.  */
void
mt_expand_eh_return (rtx * operands)
{
  if (GET_CODE (operands[0]) != REG
      || REGNO (operands[0]) != EH_RETURN_STACKADJ_REGNO)
    {
      rtx sp = EH_RETURN_STACKADJ_RTX;

      emit_move_insn (sp, operands[0]);
      operands[0] = sp;
    }

  emit_insn (gen_eh_epilogue (operands[0]));
}

/* Generate code for the "eh_epilogue" pattern.  */
void
mt_emit_eh_epilogue (rtx * operands ATTRIBUTE_UNUSED)
{
  cfun->machine->eh_stack_adjust = EH_RETURN_STACKADJ_RTX; /* operands[0]; */
  mt_expand_epilogue (EH_EPILOGUE);
}

/* Handle an "interrupt" attribute.  */
static tree
mt_handle_interrupt_attribute (tree * node,
			  tree   name,
			  tree   args  ATTRIBUTE_UNUSED,
			  int    flags ATTRIBUTE_UNUSED,
			  bool * no_add_attrs)
{
  if (TREE_CODE (*node) != FUNCTION_DECL)
    {
      warning (OPT_Wattributes,
	       "%qs attribute only applies to functions",
	       IDENTIFIER_POINTER (name));
      *no_add_attrs = true;
    }

  return NULL_TREE;
}

/* Table of machine attributes.  */
const struct attribute_spec mt_attribute_table[] =
{
  /* name,        min, max, decl?, type?, func?, handler  */
  { "interrupt",  0,   0,   false, false, false, mt_handle_interrupt_attribute },
  { NULL,         0,   0,   false, false, false, NULL }
};

/* Implement INITIAL_ELIMINATION_OFFSET.  */
int
mt_initial_elimination_offset (int from, int to)
{
  mt_compute_frame_size (get_frame_size ());

  if (from == FRAME_POINTER_REGNUM && to == STACK_POINTER_REGNUM)
    return 0;

  else if (from == ARG_POINTER_REGNUM && to == STACK_POINTER_REGNUM)
    return current_frame_info.total_size;

  else if (from == ARG_POINTER_REGNUM && to == FRAME_POINTER_REGNUM)
    return current_frame_info.total_size;

  else
    gcc_unreachable ();
}

/* Generate a compare for CODE.  Return a brand-new rtx that
   represents the result of the compare.  */

static rtx
mt_generate_compare (enum rtx_code code, rtx op0, rtx op1)
{
  rtx scratch0, scratch1, const_scratch;

  switch (code)
    {
    case GTU:
    case LTU:
    case GEU:
    case LEU:
      /* Need to adjust ranges for faking unsigned compares.  */
      scratch0 = gen_reg_rtx (SImode);
      scratch1 = gen_reg_rtx (SImode);
      const_scratch = force_reg (SImode, GEN_INT(MT_MIN_INT));
      emit_insn (gen_addsi3 (scratch0, const_scratch, op0));
      emit_insn (gen_addsi3 (scratch1, const_scratch, op1));
      break;
    default:
      scratch0 = op0;
      scratch1 = op1;
      break;
    }
    
  /* Adjust compare operator to fake unsigned compares.  */
  switch (code)
    {
    case GTU:
      code = GT; break;
    case LTU:
      code = LT; break;
    case GEU:
      code = GE; break;
    case LEU:
      code = LE; break;
    default:
      /* do nothing */
      break;
    }

  /* Generate the actual compare.  */
  return gen_rtx_fmt_ee (code, VOIDmode, scratch0, scratch1);
}

/* Emit a branch of kind CODE to location LOC.  */

void
mt_emit_cbranch (enum rtx_code code, rtx loc, rtx op0, rtx op1)
{
  rtx condition_rtx, loc_ref;

  if (! reg_or_0_operand (op0, SImode))
    op0 = copy_to_mode_reg (SImode, op0);

  if (! reg_or_0_operand (op1, SImode))
    op1 = copy_to_mode_reg (SImode, op1);

  condition_rtx = mt_generate_compare (code, op0, op1);
  loc_ref = gen_rtx_LABEL_REF (VOIDmode, loc);
  emit_jump_insn (gen_rtx_SET (VOIDmode, pc_rtx,
			       gen_rtx_IF_THEN_ELSE (VOIDmode, condition_rtx,
						     loc_ref, pc_rtx)));
}

/* Subfunction of the following function.  Update the flags of any MEM
   found in part of X.  */

static void
mt_set_memflags_1 (rtx x, int in_struct_p, int volatile_p)
{
  int i;

  switch (GET_CODE (x))
    {
    case SEQUENCE:
    case PARALLEL:
      for (i = XVECLEN (x, 0) - 1; i >= 0; i--)
	mt_set_memflags_1 (XVECEXP (x, 0, i), in_struct_p, volatile_p);
      break;

    case INSN:
      mt_set_memflags_1 (PATTERN (x), in_struct_p, volatile_p);
      break;

    case SET:
      mt_set_memflags_1 (SET_DEST (x), in_struct_p, volatile_p);
      mt_set_memflags_1 (SET_SRC (x), in_struct_p, volatile_p);
      break;

    case MEM:
      MEM_IN_STRUCT_P (x) = in_struct_p;
      MEM_VOLATILE_P (x) = volatile_p;
      /* Sadly, we cannot use alias sets because the extra aliasing
	 produced by the AND interferes.  Given that two-byte quantities
	 are the only thing we would be able to differentiate anyway,
	 there does not seem to be any point in convoluting the early
	 out of the alias check.  */
      /* set_mem_alias_set (x, alias_set); */
      break;

    default:
      break;
    }
}

/* Look for any MEMs in the current sequence of insns and set the
   in-struct, unchanging, and volatile flags from the flags in REF.
   If REF is not a MEM, don't do anything.  */

void
mt_set_memflags (rtx ref)
{
  rtx insn;
  int in_struct_p, volatile_p;

  if (GET_CODE (ref) != MEM)
    return;

  in_struct_p = MEM_IN_STRUCT_P (ref);
  volatile_p = MEM_VOLATILE_P (ref);

  /* This is only called from mt.md, after having had something 
     generated from one of the insn patterns.  So if everything is
     zero, the pattern is already up-to-date.  */
  if (! in_struct_p && ! volatile_p)
    return;

  for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
    mt_set_memflags_1 (insn, in_struct_p, volatile_p);
}

/* Implement SECONDARY_RELOAD_CLASS.  */
enum reg_class
mt_secondary_reload_class (enum reg_class class ATTRIBUTE_UNUSED,
			    enum machine_mode mode,
			    rtx x)
{
  if ((mode == QImode && (!TARGET_BYTE_ACCESS)) || mode == HImode)
    {
      if (GET_CODE (x) == MEM
	  || (GET_CODE (x) == REG && true_regnum (x) == -1)
	  || (GET_CODE (x) == SUBREG
	      && (GET_CODE (SUBREG_REG (x)) == MEM
		  || (GET_CODE (SUBREG_REG (x)) == REG
		      && true_regnum (SUBREG_REG (x)) == -1))))
	return GENERAL_REGS;
    }

  return NO_REGS;
}

/* Handle FUNCTION_VALUE, FUNCTION_OUTGOING_VALUE, and LIBCALL_VALUE
   macros.  */
rtx
mt_function_value (tree valtype, enum machine_mode mode, tree func_decl ATTRIBUTE_UNUSED)
{
  if ((mode) == DImode || (mode) == DFmode)
    return gen_rtx_MEM (mode, gen_rtx_REG (mode, RETURN_VALUE_REGNUM));

  if (valtype)
    mode = TYPE_MODE (valtype);

  return gen_rtx_REG (mode, RETURN_VALUE_REGNUM);
}

/* Split a move into two smaller pieces.
   MODE indicates the reduced mode.  OPERANDS[0] is the original destination
   OPERANDS[1] is the original src.  The new destinations are
   OPERANDS[2] and OPERANDS[4], while the new sources are OPERANDS[3]
   and OPERANDS[5].  */

void
mt_split_words (enum machine_mode nmode,
		 enum machine_mode omode,
		 rtx *operands)
{
  rtx dl,dh;	/* src/dest pieces.  */
  rtx sl,sh;
  int	move_high_first = 0;	/* Assume no overlap.  */

  switch (GET_CODE (operands[0])) /* Dest.  */
    {
    case SUBREG:
    case REG:
      if ((GET_CODE (operands[1]) == REG
	   || GET_CODE (operands[1]) == SUBREG)
	  && true_regnum (operands[0]) <= true_regnum (operands[1]))
	move_high_first = 1;

      if (GET_CODE (operands[0]) == SUBREG)
	{
	  dl = gen_rtx_SUBREG (nmode, SUBREG_REG (operands[0]),
			       SUBREG_BYTE (operands[0]) + GET_MODE_SIZE (nmode));
	  dh = gen_rtx_SUBREG (nmode, SUBREG_REG (operands[0]), SUBREG_BYTE (operands[0]));
	}
      else if (GET_CODE (operands[0]) == REG && ! IS_PSEUDO_P (operands[0]))
	{
	  int	r = REGNO (operands[0]);
	  dh = gen_rtx_REG (nmode, r);
	  dl = gen_rtx_REG (nmode, r + HARD_REGNO_NREGS (r, nmode));
	}
      else
	{
	  dh = gen_rtx_SUBREG (nmode, operands[0], 0);
	  dl = gen_rtx_SUBREG (nmode, operands[0], GET_MODE_SIZE (nmode));
	}
      break;

    case MEM:
      switch (GET_CODE (XEXP (operands[0], 0)))
	{
	case POST_INC:
	case POST_DEC:
	  gcc_unreachable ();
	default:
	  dl = operand_subword (operands[0],
				GET_MODE_SIZE (nmode)/UNITS_PER_WORD,
				0, omode);
	  dh = operand_subword (operands[0], 0, 0, omode);
	}
      break;
    default:
      gcc_unreachable ();
    }

  switch (GET_CODE (operands[1]))
    {
    case REG:
      if (! IS_PSEUDO_P (operands[1]))
	{
	  int r = REGNO (operands[1]);

	  sh = gen_rtx_REG (nmode, r);
	  sl = gen_rtx_REG (nmode, r + HARD_REGNO_NREGS (r, nmode));
	}
      else
	{
	  sh = gen_rtx_SUBREG (nmode, operands[1], 0);
	  sl = gen_rtx_SUBREG (nmode, operands[1], GET_MODE_SIZE (nmode));
	}
      break;

    case CONST_DOUBLE:
      if (operands[1] == const0_rtx)
	sh = sl = const0_rtx;
      else
	split_double (operands[1], & sh, & sl);
      break;

    case CONST_INT:
      if (operands[1] == const0_rtx)
	sh = sl = const0_rtx;
      else
	{
	  int vl, vh;

	  switch (nmode)
	    {
	    default:
	      gcc_unreachable ();
	    }
	    
	  sl = GEN_INT (vl);
	  sh = GEN_INT (vh);
	}
      break;

    case SUBREG:
      sl = gen_rtx_SUBREG (nmode,
			   SUBREG_REG (operands[1]),
			   SUBREG_BYTE (operands[1]) + GET_MODE_SIZE (nmode));
      sh = gen_rtx_SUBREG (nmode,
			   SUBREG_REG (operands[1]),
			   SUBREG_BYTE (operands[1]));
      break;

    case MEM:
      switch (GET_CODE (XEXP (operands[1], 0)))
	{
	case POST_DEC:
	case POST_INC:
	  gcc_unreachable ();
	  break;
	default:
	  sl = operand_subword (operands[1], 
				GET_MODE_SIZE (nmode)/UNITS_PER_WORD,
				0, omode);
	  sh = operand_subword (operands[1], 0, 0, omode);
	  
	  /* Check if the DF load is going to clobber the register
             used for the address, and if so make sure that is going
             to be the second move.  */
	  if (GET_CODE (dl) == REG
	      && true_regnum (dl)
	      == true_regnum (XEXP (XEXP (sl, 0 ), 0)))
	    move_high_first = 1;
	}
      break;
    default:
      gcc_unreachable ();
    }

  if (move_high_first)
    {
      operands[2] = dh;
      operands[3] = sh;
      operands[4] = dl;
      operands[5] = sl;
    }
  else
    {
      operands[2] = dl;
      operands[3] = sl;
      operands[4] = dh;
      operands[5] = sh;
    }
  return;
}

/* Implement TARGET_MUST_PASS_IN_STACK hook.  */
static bool
mt_pass_in_stack (enum machine_mode mode ATTRIBUTE_UNUSED, tree type)
{
  return (((type) != 0
	   && (TREE_CODE (TYPE_SIZE (type)) != INTEGER_CST
	       || TREE_ADDRESSABLE (type))));
}

/* Increment the counter for the number of loop instructions in the
   current function.  */

void mt_add_loop (void)
{
  cfun->machine->has_loops++;
}


/* Maximum loop nesting depth.  */
#define MAX_LOOP_DEPTH 4
/* Maximum size of a loop (allows some headroom for delayed branch slot
   filling.  */
#define MAX_LOOP_LENGTH (200 * 4)

/* We need to keep a vector of loops */
typedef struct loop_info *loop_info;
DEF_VEC_P (loop_info);
DEF_VEC_ALLOC_P (loop_info,heap);

/* Information about a loop we have found (or are in the process of
   finding).  */
struct loop_info GTY (())
{
  /* loop number, for dumps */
  int loop_no;
  
  /* Predecessor block of the loop.   This is the one that falls into
     the loop and contains the initialization instruction.  */
  basic_block predecessor;

  /* First block in the loop.  This is the one branched to by the dbnz
     insn.  */
  basic_block head;
  
  /* Last block in the loop (the one with the dbnz insn */
  basic_block tail;

  /* The successor block of the loop.  This is the one the dbnz insn
     falls into.  */
  basic_block successor;

  /* The dbnz insn.  */
  rtx dbnz;

  /* The initialization insn.  */
  rtx init;

  /* The new initialization instruction.  */
  rtx loop_init;

  /* The new ending instruction. */
  rtx loop_end;

  /* The new label placed at the end of the loop. */
  rtx end_label;

  /* The nesting depth of the loop.  Set to -1 for a bad loop.  */
  int depth;

  /* The length of the loop.  */
  int length;

  /* Next loop in the graph. */
  struct loop_info *next;

  /* Vector of blocks only within the loop, (excluding those within
     inner loops).  */
  VEC (basic_block,heap) *blocks;

  /* Vector of inner loops within this loop  */
  VEC (loop_info,heap) *loops;
};

/* Information used during loop detection.  */
typedef struct loop_work GTY(())
{
  /* Basic block to be scanned.  */
  basic_block block;

  /* Loop it will be within.  */
  loop_info loop;
} loop_work;

/* Work list.  */
DEF_VEC_O (loop_work);
DEF_VEC_ALLOC_O (loop_work,heap);

/* Determine the nesting and length of LOOP.  Return false if the loop
   is bad.  */

static bool
mt_loop_nesting (loop_info loop)
{
  loop_info inner;
  unsigned ix;
  int inner_depth = 0;
  
  if (!loop->depth)
    {
      /* Make sure we only have one entry point.  */
      if (EDGE_COUNT (loop->head->preds) == 2)
	{
	  loop->predecessor = EDGE_PRED (loop->head, 0)->src;
	  if (loop->predecessor == loop->tail)
	    /* We wanted the other predecessor.  */
	    loop->predecessor = EDGE_PRED (loop->head, 1)->src;
	  
	  /* We can only place a loop insn on a fall through edge of a
	     single exit block.  */
	  if (EDGE_COUNT (loop->predecessor->succs) != 1
	      || !(EDGE_SUCC (loop->predecessor, 0)->flags & EDGE_FALLTHRU))
	    loop->predecessor = NULL;
	}

      /* Mark this loop as bad for now.  */
      loop->depth = -1;
      if (loop->predecessor)
	{
	  for (ix = 0; VEC_iterate (loop_info, loop->loops, ix++, inner);)
	    {
	      if (!inner->depth)
		mt_loop_nesting (inner);
	      
	      if (inner->depth < 0)
		{
		  inner_depth = -1;
		  break;
		}
	      
	      if (inner_depth < inner->depth)
		inner_depth = inner->depth;
	      loop->length += inner->length;
	    }
	  
	  /* Set the proper loop depth, if it was good. */
	  if (inner_depth >= 0)
	    loop->depth = inner_depth + 1;
	}
    }
  return (loop->depth > 0
	  && loop->predecessor
	  && loop->depth < MAX_LOOP_DEPTH
	  && loop->length < MAX_LOOP_LENGTH);
}

/* Determine the length of block BB.  */

static int
mt_block_length (basic_block bb)
{
  int length = 0;
  rtx insn;

  for (insn = BB_HEAD (bb);
       insn != NEXT_INSN (BB_END (bb));
       insn = NEXT_INSN (insn))
    {
      if (!INSN_P (insn))
	continue;
      if (CALL_P (insn))
	{
	  /* Calls are not allowed in loops.  */
	  length = MAX_LOOP_LENGTH + 1;
	  break;
	}
      
      length += get_attr_length (insn);
    }
  return length;
}

/* Scan the blocks of LOOP (and its inferiors) looking for uses of
   REG.  Return true, if we find any.  Don't count the loop's dbnz
   insn if it matches DBNZ.  */

static bool
mt_scan_loop (loop_info loop, rtx reg, rtx dbnz)
{
  unsigned ix;
  loop_info inner;
  basic_block bb;
  
  for (ix = 0; VEC_iterate (basic_block, loop->blocks, ix, bb); ix++)
    {
      rtx insn;

      for (insn = BB_HEAD (bb);
	   insn != NEXT_INSN (BB_END (bb));
	   insn = NEXT_INSN (insn))
	{
	  if (!INSN_P (insn))
	    continue;
	  if (insn == dbnz)
	    continue;
	  if (reg_mentioned_p (reg, PATTERN (insn)))
	    return true;
	}
    }
  for (ix = 0; VEC_iterate (loop_info, loop->loops, ix, inner); ix++)
    if (mt_scan_loop (inner, reg, NULL_RTX))
      return true;
  
  return false;
}

/* MS2 has a loop instruction which needs to be placed just before the
   loop.  It indicates the end of the loop and specifies the number of
   loop iterations.  It can be nested with an automatically maintained
   stack of counter and end address registers.  It's an ideal
   candidate for doloop.  Unfortunately, gcc presumes that loops
   always end with an explicit instruction, and the doloop_begin
   instruction is not a flow control instruction so it can be
   scheduled earlier than just before the start of the loop.  To make
   matters worse, the optimization pipeline can duplicate loop exit
   and entrance blocks and fails to track abnormally exiting loops.
   Thus we cannot simply use doloop.

   What we do is emit a dbnz pattern for the doloop optimization, and
   let that be optimized as normal.  Then in machine dependent reorg
   we have to repeat the loop searching algorithm.  We use the
   flow graph to find closed loops ending in a dbnz insn.  We then try
   and convert it to use the loop instruction.  The conditions are,

   * the loop has no abnormal exits, duplicated end conditions or
   duplicated entrance blocks

   * the loop counter register is only used in the dbnz instruction
   within the loop
   
   * we can find the instruction setting the initial value of the loop
   counter

   * the loop is not executed more than 65535 times. (This might be
   changed to 2^32-1, and would therefore allow variable initializers.)

   * the loop is not nested more than 4 deep 5) there are no
   subroutine calls in the loop.  */

static void
mt_reorg_loops (FILE *dump_file)
{
  basic_block bb;
  loop_info loops = NULL;
  loop_info loop;
  int nloops = 0;
  unsigned dwork = 0;
  VEC (loop_work,heap) *works = VEC_alloc (loop_work,heap,20);
  loop_work *work;
  edge e;
  edge_iterator ei;
  bool replaced = false;

  /* Find all the possible loop tails.  This means searching for every
     dbnz instruction.  For each one found, create a loop_info
     structure and add the head block to the work list. */
  FOR_EACH_BB (bb)
    {
      rtx tail = BB_END (bb);

      while (GET_CODE (tail) == NOTE)
	tail = PREV_INSN (tail);
      
      bb->aux = NULL;
      if (recog_memoized (tail) == CODE_FOR_decrement_and_branch_until_zero)
	{
	  /* A possible loop end */

	  loop = XNEW (struct loop_info);
	  loop->next = loops;
	  loops = loop;
	  loop->tail = bb;
	  loop->head = BRANCH_EDGE (bb)->dest;
	  loop->successor = FALLTHRU_EDGE (bb)->dest;
	  loop->predecessor = NULL;
	  loop->dbnz = tail;
	  loop->depth = 0;
	  loop->length = mt_block_length (bb);
	  loop->blocks = VEC_alloc (basic_block, heap, 20);
	  VEC_quick_push (basic_block, loop->blocks, bb);
	  loop->loops = NULL;
	  loop->loop_no = nloops++;
	  
	  loop->init = loop->end_label = NULL_RTX;
	  loop->loop_init = loop->loop_end = NULL_RTX;
	  
	  work = VEC_safe_push (loop_work, heap, works, NULL);
	  work->block = loop->head;
	  work->loop = loop;

	  bb->aux = loop;

	  if (dump_file)
	    {
	      fprintf (dump_file, ";; potential loop %d ending at\n",
		       loop->loop_no);
	      print_rtl_single (dump_file, tail);
	    }
	}
    }

  /*  Now find all the closed loops.
      until work list empty,
       if block's auxptr is set
         if != loop slot
           if block's loop's start != block
	     mark loop as bad
	   else
             append block's loop's fallthrough block to worklist
	     increment this loop's depth
       else if block is exit block
         mark loop as bad
       else
     	  set auxptr
	  for each target of block
     	    add to worklist */
  while (VEC_iterate (loop_work, works, dwork++, work))
    {
      loop = work->loop;
      bb = work->block;
      if (bb == EXIT_BLOCK_PTR)
	/* We've reached the exit block.  The loop must be bad. */
	loop->depth = -1;
      else if (!bb->aux)
	{
	  /* We've not seen this block before.  Add it to the loop's
	     list and then add each successor to the work list.  */
	  bb->aux = loop;
	  loop->length += mt_block_length (bb);
	  VEC_safe_push (basic_block, heap, loop->blocks, bb);
	  FOR_EACH_EDGE (e, ei, bb->succs)
	    {
	      if (!VEC_space (loop_work, works, 1))
		{
		  if (dwork)
		    {
		      VEC_block_remove (loop_work, works, 0, dwork);
		      dwork = 0;
		    }
		  else
		    VEC_reserve (loop_work, heap, works, 1);
		}
	      work = VEC_quick_push (loop_work, works, NULL);
	      work->block = EDGE_SUCC (bb, ei.index)->dest;
	      work->loop = loop;
	    }
	}
      else if (bb->aux != loop)
	{
	  /* We've seen this block in a different loop.  If it's not
	     the other loop's head, then this loop must be bad.
	     Otherwise, the other loop might be a nested loop, so
	     continue from that loop's successor.  */
	  loop_info other = bb->aux;
	  
	  if (other->head != bb)
	    loop->depth = -1;
	  else
	    {
	      VEC_safe_push (loop_info, heap, loop->loops, other);
	      work = VEC_safe_push (loop_work, heap, works, NULL);
	      work->loop = loop;
	      work->block = other->successor;
	    }
	}
    }
  VEC_free (loop_work, heap, works);

  /* Now optimize the loops.  */
  for (loop = loops; loop; loop = loop->next)
    {
      rtx iter_reg, insn, init_insn;
      rtx init_val, loop_end, loop_init, end_label, head_label;

      if (!mt_loop_nesting (loop))
	{
	  if (dump_file)
	    fprintf (dump_file, ";; loop %d is bad\n", loop->loop_no);
	  continue;
	}

      /* Get the loop iteration register.  */
      iter_reg = SET_DEST (XVECEXP (PATTERN (loop->dbnz), 0, 1));
      
      if (!REG_P (iter_reg))
	{
	  /* Spilled */
	  if (dump_file)
	    fprintf (dump_file, ";; loop %d has spilled iteration count\n",
		     loop->loop_no);
	  continue;
	}

      /* Look for the initializing insn */
      init_insn = NULL_RTX;
      for (insn = BB_END (loop->predecessor);
	   insn != PREV_INSN (BB_HEAD (loop->predecessor));
	   insn = PREV_INSN (insn))
	{
	  if (!INSN_P (insn))
	    continue;
	  if (reg_mentioned_p (iter_reg, PATTERN (insn)))
	    {
	      rtx set = single_set (insn);

	      if (set && rtx_equal_p (iter_reg, SET_DEST (set)))
		init_insn = insn;
	      break;
	    }
	}

      if (!init_insn)
	{
	  if (dump_file)
	    fprintf (dump_file, ";; loop %d has no initializer\n",
		     loop->loop_no);
	  continue;
	}
      if (dump_file)
	{
	  fprintf (dump_file, ";; loop %d initialized by\n",
		   loop->loop_no);
	  print_rtl_single (dump_file, init_insn);
	}

      init_val = PATTERN (init_insn);
      if (GET_CODE (init_val) == SET)
	init_val = SET_SRC (init_val);
      if (GET_CODE (init_val) != CONST_INT || INTVAL (init_val) >= 65535)
	{
	  if (dump_file)
	    fprintf (dump_file, ";; loop %d has complex initializer\n",
		     loop->loop_no);
	  continue;
	}
      
      /* Scan all the blocks to make sure they don't use iter_reg.  */
      if (mt_scan_loop (loop, iter_reg, loop->dbnz))
	{
	  if (dump_file)
	    fprintf (dump_file, ";; loop %d uses iterator\n",
		     loop->loop_no);
	  continue;
	}

      /* The loop is good for replacement.  */
      
      /* loop is 1 based, dbnz is zero based.  */
      init_val = GEN_INT (INTVAL (init_val) + 1);
      
      iter_reg = gen_rtx_REG (SImode, LOOP_FIRST + loop->depth - 1);
      end_label = gen_label_rtx ();
      head_label = XEXP (SET_SRC (XVECEXP (PATTERN (loop->dbnz), 0, 0)), 1);
      loop_end = gen_loop_end (iter_reg, head_label);
      loop_init = gen_loop_init (iter_reg, init_val, end_label);
      loop->init = init_insn;
      loop->end_label = end_label;
      loop->loop_init = loop_init;
      loop->loop_end = loop_end;
      replaced = true;
      
      if (dump_file)
	{
	  fprintf (dump_file, ";; replacing loop %d initializer with\n",
		   loop->loop_no);
	  print_rtl_single (dump_file, loop->loop_init);
	  fprintf (dump_file, ";; replacing loop %d terminator with\n",
		   loop->loop_no);
	  print_rtl_single (dump_file, loop->loop_end);
	}
    }

  /* Now apply the optimizations.  Do it this way so we don't mess up
     the flow graph half way through.  */
  for (loop = loops; loop; loop = loop->next)
    if (loop->loop_init)
      {
	emit_jump_insn_after (loop->loop_init, BB_END (loop->predecessor));
	delete_insn (loop->init);
	emit_label_before (loop->end_label, loop->dbnz);
	emit_jump_insn_before (loop->loop_end, loop->dbnz);
	delete_insn (loop->dbnz);
      }

  /* Free up the loop structures */
  while (loops)
    {
      loop = loops;
      loops = loop->next;
      VEC_free (loop_info, heap, loop->loops);
      VEC_free (basic_block, heap, loop->blocks);
      XDELETE (loop);
    }

  if (replaced && dump_file)
    {
      fprintf (dump_file, ";; Replaced loops\n");
      print_rtl (dump_file, get_insns ());
    }
}

/* Structures to hold branch information during reorg.  */
typedef struct branch_info
{
  rtx insn;  /* The branch insn.  */
  
  struct branch_info *next;
} branch_info;

typedef struct label_info
{
  rtx label;  /* The label.  */
  branch_info *branches;  /* branches to this label.  */
  struct label_info *next;
} label_info;

/* Chain of labels found in current function, used during reorg.  */
static label_info *mt_labels;

/* If *X is a label, add INSN to the list of branches for that
   label.  */

static int
mt_add_branches (rtx *x, void *insn)
{
  if (GET_CODE (*x) == LABEL_REF)
    {
      branch_info *branch = xmalloc (sizeof (*branch));
      rtx label = XEXP (*x, 0);
      label_info *info;

      for (info = mt_labels; info; info = info->next)
	if (info->label == label)
	  break;

      if (!info)
	{
	  info = xmalloc (sizeof (*info));
	  info->next = mt_labels;
	  mt_labels = info;
	  
	  info->label = label;
	  info->branches = NULL;
	}

      branch->next = info->branches;
      info->branches = branch;
      branch->insn = insn;
    }
  return 0;
}

/* If BRANCH has a filled delay slot, check if INSN is dependent upon
   it.  If so, undo the delay slot fill.   Returns the next insn, if
   we patch out the branch.  Returns the branch insn, if we cannot
   patch out the branch (due to anti-dependency in the delay slot).
   In that case, the caller must insert nops at the branch target.  */

static rtx
mt_check_delay_slot (rtx branch, rtx insn)
{
  rtx slot;
  rtx tmp;
  rtx p;
  rtx jmp;
  
  gcc_assert (GET_CODE (PATTERN (branch)) == SEQUENCE);
  if (INSN_DELETED_P (branch))
    return NULL_RTX;
  slot = XVECEXP (PATTERN (branch), 0, 1);
  
  tmp = PATTERN (insn);
  note_stores (PATTERN (slot), insn_dependent_p_1, &tmp);
  if (tmp)
    /* Not dependent.  */
    return NULL_RTX;
  
  /* Undo the delay slot.  */
  jmp = XVECEXP (PATTERN (branch), 0, 0);
  
  tmp = PATTERN (jmp);
  note_stores (PATTERN (slot), insn_dependent_p_1, &tmp);
  if (!tmp)
    /* Anti dependent. */
    return branch;
      
  p = PREV_INSN (branch);
  NEXT_INSN (p) = slot;
  PREV_INSN (slot) = p;
  NEXT_INSN (slot) = jmp;
  PREV_INSN (jmp) = slot;
  NEXT_INSN (jmp) = branch;
  PREV_INSN (branch) = jmp;
  XVECEXP (PATTERN (branch), 0, 0) = NULL_RTX;
  XVECEXP (PATTERN (branch), 0, 1) = NULL_RTX;
  delete_insn (branch);
  return jmp;
}

/* Insert nops to satisfy pipeline constraints.  We only deal with ms2
   constraints here.  Earlier CPUs are dealt with by inserting nops with
   final_prescan (but that can lead to inferior code, and is
   impractical with ms2's JAL hazard).

   ms2 dynamic constraints
   1) a load and a following use must be separated by one insn
   2) an insn and a following dependent call must be separated by two insns
   
   only arith insns are placed in delay slots so #1 cannot happen with
   a load in a delay slot.  #2 can happen with an arith insn in the
   delay slot.  */

static void
mt_reorg_hazard (void)
{
  rtx insn, next;

  /* Find all the branches */
  for (insn = get_insns ();
       insn;
       insn = NEXT_INSN (insn))
    {
      rtx jmp;

      if (!INSN_P (insn))
	continue;

      jmp = PATTERN (insn);
      
      if (GET_CODE (jmp) != SEQUENCE)
	/* If it's not got a filled delay slot, then it can't
	   conflict.  */
	continue;
      
      jmp = XVECEXP (jmp, 0, 0);

      if (recog_memoized (jmp) == CODE_FOR_tablejump)
	for (jmp = XEXP (XEXP (XVECEXP (PATTERN (jmp), 0, 1), 0), 0);
	     !JUMP_TABLE_DATA_P (jmp);
	     jmp = NEXT_INSN (jmp))
	  continue;

      for_each_rtx (&PATTERN (jmp), mt_add_branches, insn);
    }

  /* Now scan for dependencies.  */
  for (insn = get_insns ();
       insn && !INSN_P (insn);
       insn = NEXT_INSN (insn))
    continue;
  
  for (;
       insn;
       insn = next)
    {
      rtx jmp, tmp;
      enum attr_type attr;
      
      gcc_assert (INSN_P (insn) && !INSN_DELETED_P (insn));
      for (next = NEXT_INSN (insn);
	   next;
	   next = NEXT_INSN (next))
	{
	  if (!INSN_P (next))
	    continue;
	  if (GET_CODE (PATTERN (next)) != USE)
	    break;
	}

      jmp = insn;
      if (GET_CODE (PATTERN (insn)) == SEQUENCE)
	jmp = XVECEXP (PATTERN (insn), 0, 0);
      
      attr = recog_memoized (jmp) >= 0 ? get_attr_type (jmp) : TYPE_UNKNOWN;
      
      if (next && attr == TYPE_LOAD)
	{
	  /* A load.  See if NEXT is dependent, and if so insert a
	     nop.  */
	  
	  tmp = PATTERN (next);
	  if (GET_CODE (tmp) == SEQUENCE)
	    tmp = PATTERN (XVECEXP (tmp, 0, 0));
	  note_stores (PATTERN (insn), insn_dependent_p_1, &tmp);
	  if (!tmp)
	    emit_insn_after (gen_nop (), insn);
	}
      
      if (attr == TYPE_CALL)
	{
	  /* A call.  Make sure we're not dependent on either of the
	     previous two dynamic instructions.  */
	  int nops = 0;
	  int count;
	  rtx prev = insn;
	  rtx rescan = NULL_RTX;

	  for (count = 2; count && !nops;)
	    {
	      int type;
	      
	      prev = PREV_INSN (prev);
	      if (!prev)
		{
		  /* If we reach the start of the function, we must
		     presume the caller set the address in the delay
		     slot of the call instruction.  */
		  nops = count;
		  break;
		}
	      
	      if (BARRIER_P (prev))
		break;
	      if (LABEL_P (prev))
		{
		  /* Look at branches to this label.  */
		  label_info *label;
		  branch_info *branch;

		  for (label = mt_labels;
		       label;
		       label = label->next)
		    if (label->label == prev)
		      {
			for (branch = label->branches;
			     branch;
			     branch = branch->next)
			  {
			    tmp = mt_check_delay_slot (branch->insn, jmp);

			    if (tmp == branch->insn)
			      {
				nops = count;
				break;
			      }
			    
			    if (tmp && branch->insn == next)
			      rescan = tmp;
			  }
			break;
		      }
		  continue;
		}
	      if (!INSN_P (prev) || GET_CODE (PATTERN (prev)) == USE)
		continue;
	      
	      if (GET_CODE (PATTERN (prev)) == SEQUENCE)
		{
		  /* Look at the delay slot.  */
		  tmp = mt_check_delay_slot (prev, jmp);
		  if (tmp == prev)
		    nops = count;
		  break;
		}
	      
	      type = (INSN_CODE (prev) >= 0 ? get_attr_type (prev)
		      : TYPE_COMPLEX);
	      if (type == TYPE_CALL || type == TYPE_BRANCH)
		break;
	      
	      if (type == TYPE_LOAD
		  || type == TYPE_ARITH
		  || type == TYPE_COMPLEX)
		{
		  tmp = PATTERN (jmp);
		  note_stores (PATTERN (prev), insn_dependent_p_1, &tmp);
		  if (!tmp)
		    {
		      nops = count;
		      break;
		    }
		}

	      if (INSN_CODE (prev) >= 0)
		count--;
	    }

	  if (rescan)
	    for (next = NEXT_INSN (rescan);
		 next && !INSN_P (next);
		 next = NEXT_INSN (next))
	      continue;
	  while (nops--)
	    emit_insn_before (gen_nop (), insn);
	}
    }

  /* Free the data structures.  */
  while (mt_labels)
    {
      label_info *label = mt_labels;
      branch_info *branch, *next;
      
      mt_labels = label->next;
      for (branch = label->branches; branch; branch = next)
	{
	  next = branch->next;
	  free (branch);
	}
      free (label);
    }
}

/* Fixup the looping instructions, do delayed branch scheduling, fixup
   scheduling hazards.  */

static void
mt_machine_reorg (void)
{
  if (cfun->machine->has_loops && TARGET_MS2)
    mt_reorg_loops (dump_file);

  if (mt_flag_delayed_branch)
    dbr_schedule (get_insns ());
  
  if (TARGET_MS2)
    {
      /* Force all instructions to be split into their final form.  */
      split_all_insns_noflow ();
      mt_reorg_hazard ();
    }
}

/* Initialize the GCC target structure.  */
const struct attribute_spec mt_attribute_table[];

#undef  TARGET_ATTRIBUTE_TABLE
#define TARGET_ATTRIBUTE_TABLE 		mt_attribute_table
#undef  TARGET_STRUCT_VALUE_RTX
#define TARGET_STRUCT_VALUE_RTX		mt_struct_value_rtx
#undef  TARGET_PROMOTE_PROTOTYPES
#define TARGET_PROMOTE_PROTOTYPES	hook_bool_tree_true
#undef  TARGET_PASS_BY_REFERENCE
#define TARGET_PASS_BY_REFERENCE	mt_pass_by_reference
#undef  TARGET_MUST_PASS_IN_STACK
#define TARGET_MUST_PASS_IN_STACK       mt_pass_in_stack
#undef  TARGET_ARG_PARTIAL_BYTES
#define TARGET_ARG_PARTIAL_BYTES	mt_arg_partial_bytes
#undef  TARGET_SETUP_INCOMING_VARARGS
#define TARGET_SETUP_INCOMING_VARARGS 	mt_setup_incoming_varargs
#undef  TARGET_MACHINE_DEPENDENT_REORG
#define TARGET_MACHINE_DEPENDENT_REORG  mt_machine_reorg

struct gcc_target targetm = TARGET_INITIALIZER;

#include "gt-mt.h"
