/* Definitions of target machine for GNU compiler.
   Copyright (C) 1999, 2000, 2001 Free Software Foundation, Inc.
   Contributed by James E. Wilson <wilson@cygnus.com> and
   		  David Mosberger <davidm@hpl.hp.com>.

This file is part of GNU CC.

GNU CC 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.

GNU CC 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 GNU CC; see the file COPYING.  If not, write to
the Free Software Foundation, 59 Temple Place - Suite 330,
Boston, MA 02111-1307, USA.  */

#include "config.h"
#include "system.h"
#include "rtl.h"
#include "tree.h"
#include "tm_p.h"
#include "regs.h"
#include "hard-reg-set.h"
#include "real.h"
#include "insn-config.h"
#include "conditions.h"
#include "output.h"
#include "insn-attr.h"
#include "flags.h"
#include "recog.h"
#include "expr.h"
#include "obstack.h"
#include "except.h"
#include "function.h"
#include "ggc.h"
#include "basic-block.h"
#include "toplev.h"
#include "sched-int.h"

/* This is used for communication between ASM_OUTPUT_LABEL and
   ASM_OUTPUT_LABELREF.  */
int ia64_asm_output_label = 0;

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

/* Register names for ia64_expand_prologue.  */
static const char * const ia64_reg_numbers[96] =
{ "r32", "r33", "r34", "r35", "r36", "r37", "r38", "r39",
  "r40", "r41", "r42", "r43", "r44", "r45", "r46", "r47",
  "r48", "r49", "r50", "r51", "r52", "r53", "r54", "r55",
  "r56", "r57", "r58", "r59", "r60", "r61", "r62", "r63",
  "r64", "r65", "r66", "r67", "r68", "r69", "r70", "r71",
  "r72", "r73", "r74", "r75", "r76", "r77", "r78", "r79",
  "r80", "r81", "r82", "r83", "r84", "r85", "r86", "r87",
  "r88", "r89", "r90", "r91", "r92", "r93", "r94", "r95",
  "r96", "r97", "r98", "r99", "r100","r101","r102","r103",
  "r104","r105","r106","r107","r108","r109","r110","r111",
  "r112","r113","r114","r115","r116","r117","r118","r119",
  "r120","r121","r122","r123","r124","r125","r126","r127"};

/* ??? These strings could be shared with REGISTER_NAMES.  */
static const char * const ia64_input_reg_names[8] =
{ "in0",  "in1",  "in2",  "in3",  "in4",  "in5",  "in6",  "in7" };

/* ??? These strings could be shared with REGISTER_NAMES.  */
static const char * const ia64_local_reg_names[80] =
{ "loc0", "loc1", "loc2", "loc3", "loc4", "loc5", "loc6", "loc7",
  "loc8", "loc9", "loc10","loc11","loc12","loc13","loc14","loc15",
  "loc16","loc17","loc18","loc19","loc20","loc21","loc22","loc23",
  "loc24","loc25","loc26","loc27","loc28","loc29","loc30","loc31",
  "loc32","loc33","loc34","loc35","loc36","loc37","loc38","loc39",
  "loc40","loc41","loc42","loc43","loc44","loc45","loc46","loc47",
  "loc48","loc49","loc50","loc51","loc52","loc53","loc54","loc55",
  "loc56","loc57","loc58","loc59","loc60","loc61","loc62","loc63",
  "loc64","loc65","loc66","loc67","loc68","loc69","loc70","loc71",
  "loc72","loc73","loc74","loc75","loc76","loc77","loc78","loc79" };

/* ??? These strings could be shared with REGISTER_NAMES.  */
static const char * const ia64_output_reg_names[8] =
{ "out0", "out1", "out2", "out3", "out4", "out5", "out6", "out7" };

/* String used with the -mfixed-range= option.  */
const char *ia64_fixed_range_string;

/* Variables which are this size or smaller are put in the sdata/sbss
   sections.  */

unsigned int ia64_section_threshold;

static int find_gr_spill PARAMS ((int));
static int next_scratch_gr_reg PARAMS ((void));
static void mark_reg_gr_used_mask PARAMS ((rtx, void *));
static void ia64_compute_frame_size PARAMS ((HOST_WIDE_INT));
static void setup_spill_pointers PARAMS ((int, rtx, HOST_WIDE_INT));
static void finish_spill_pointers PARAMS ((void));
static rtx spill_restore_mem PARAMS ((rtx, HOST_WIDE_INT));
static void do_spill PARAMS ((rtx (*)(rtx, rtx, rtx), rtx, HOST_WIDE_INT, rtx));
static void do_restore PARAMS ((rtx (*)(rtx, rtx, rtx), rtx, HOST_WIDE_INT));
static rtx gen_movdi_x PARAMS ((rtx, rtx, rtx));
static rtx gen_fr_spill_x PARAMS ((rtx, rtx, rtx));
static rtx gen_fr_restore_x PARAMS ((rtx, rtx, rtx));

static enum machine_mode hfa_element_mode PARAMS ((tree, int));
static void fix_range PARAMS ((const char *));
static void ia64_add_gc_roots PARAMS ((void));
static void ia64_init_machine_status PARAMS ((struct function *));
static void ia64_mark_machine_status PARAMS ((struct function *));
static void ia64_free_machine_status PARAMS ((struct function *));
static void emit_insn_group_barriers PARAMS ((FILE *, rtx));
static void emit_all_insn_group_barriers PARAMS ((FILE *, rtx));
static void emit_predicate_relation_info PARAMS ((void));
static void process_epilogue PARAMS ((void));
static int process_set PARAMS ((FILE *, rtx));

static rtx ia64_expand_fetch_and_op PARAMS ((optab, enum machine_mode,
					     tree, rtx));
static rtx ia64_expand_op_and_fetch PARAMS ((optab, enum machine_mode,
					     tree, rtx));
static rtx ia64_expand_compare_and_swap PARAMS ((enum machine_mode, int,
						 tree, rtx));
static rtx ia64_expand_lock_test_and_set PARAMS ((enum machine_mode,
						  tree, rtx));
static rtx ia64_expand_lock_release PARAMS ((enum machine_mode, tree, rtx));

/* Return 1 if OP is a valid operand for the MEM of a CALL insn.  */

int
call_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  if (mode != GET_MODE (op))
    return 0;

  return (GET_CODE (op) == SYMBOL_REF || GET_CODE (op) == REG
	  || (GET_CODE (op) == SUBREG && GET_CODE (XEXP (op, 0)) == REG));
}

/* Return 1 if OP refers to a symbol in the sdata section.  */

int
sdata_symbolic_operand (op, mode)
     rtx op;
     enum machine_mode mode ATTRIBUTE_UNUSED;
{
  switch (GET_CODE (op))
    {
    case CONST:
      if (GET_CODE (XEXP (op, 0)) != PLUS
	  || GET_CODE (XEXP (XEXP (op, 0), 0)) != SYMBOL_REF)
	break;
      op = XEXP (XEXP (op, 0), 0);
      /* FALLTHRU */

    case SYMBOL_REF:
      if (CONSTANT_POOL_ADDRESS_P (op))
	return GET_MODE_SIZE (get_pool_mode (op)) <= ia64_section_threshold;
      else
        return XSTR (op, 0)[0] == SDATA_NAME_FLAG_CHAR;

    default:
      break;
    }

  return 0;
}

/* Return 1 if OP refers to a symbol, and is appropriate for a GOT load.  */

int
got_symbolic_operand (op, mode)
     rtx op;
     enum machine_mode mode ATTRIBUTE_UNUSED;
{
  switch (GET_CODE (op))
    {
    case CONST:
      op = XEXP (op, 0);
      if (GET_CODE (op) != PLUS)
	return 0;
      if (GET_CODE (XEXP (op, 0)) != SYMBOL_REF)
	return 0;
      op = XEXP (op, 1);
      if (GET_CODE (op) != CONST_INT)
	return 0;

	return 1;

      /* Ok if we're not using GOT entries at all.  */
      if (TARGET_NO_PIC || TARGET_AUTO_PIC)
	return 1;

      /* "Ok" while emitting rtl, since otherwise we won't be provided
	 with the entire offset during emission, which makes it very
	 hard to split the offset into high and low parts.  */
      if (rtx_equal_function_value_matters)
	return 1;

      /* Force the low 14 bits of the constant to zero so that we do not
	 use up so many GOT entries.  */
      return (INTVAL (op) & 0x3fff) == 0;

    case SYMBOL_REF:
    case LABEL_REF:
      return 1;

    default:
      break;
    }
  return 0;
}

/* Return 1 if OP refers to a symbol.  */

int
symbolic_operand (op, mode)
     rtx op;
     enum machine_mode mode ATTRIBUTE_UNUSED;
{
  switch (GET_CODE (op))
    {
    case CONST:
    case SYMBOL_REF:
    case LABEL_REF:
      return 1;

    default:
      break;
    }
  return 0;
}

/* Return 1 if OP refers to a function.  */

int
function_operand (op, mode)
     rtx op;
     enum machine_mode mode ATTRIBUTE_UNUSED;
{
  if (GET_CODE (op) == SYMBOL_REF && SYMBOL_REF_FLAG (op))
    return 1;
  else
    return 0;
}

/* Return 1 if OP is setjmp or a similar function.  */

/* ??? This is an unsatisfying solution.  Should rethink.  */

int
setjmp_operand (op, mode)
     rtx op;
     enum machine_mode mode ATTRIBUTE_UNUSED;
{
  const char *name;
  int retval = 0;

  if (GET_CODE (op) != SYMBOL_REF)
    return 0;

  name = XSTR (op, 0);

  /* The following code is borrowed from special_function_p in calls.c.  */

  /* Disregard prefix _, __ or __x.  */
  if (name[0] == '_')
    {
      if (name[1] == '_' && name[2] == 'x')
	name += 3;
      else if (name[1] == '_')
	name += 2;
      else
	name += 1;
    }

  if (name[0] == 's')
    {
      retval
	= ((name[1] == 'e'
	    && (! strcmp (name, "setjmp")
		|| ! strcmp (name, "setjmp_syscall")))
	   || (name[1] == 'i'
	       && ! strcmp (name, "sigsetjmp"))
	   || (name[1] == 'a'
	       && ! strcmp (name, "savectx")));
    }
  else if ((name[0] == 'q' && name[1] == 's'
	    && ! strcmp (name, "qsetjmp"))
	   || (name[0] == 'v' && name[1] == 'f'
	       && ! strcmp (name, "vfork")))
    retval = 1;

  return retval;
}

/* Return 1 if OP is a general operand, but when pic exclude symbolic
   operands.  */

/* ??? If we drop no-pic support, can delete SYMBOL_REF, CONST, and LABEL_REF
   from PREDICATE_CODES.  */

int
move_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  if (! TARGET_NO_PIC && symbolic_operand (op, mode))
    return 0;

  return general_operand (op, mode);
}

/* Return 1 if OP is a register operand that is (or could be) a GR reg.  */

int
gr_register_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  if (! register_operand (op, mode))
    return 0;
  if (GET_CODE (op) == SUBREG)
    op = SUBREG_REG (op);
  if (GET_CODE (op) == REG)
    {
      unsigned int regno = REGNO (op);
      if (regno < FIRST_PSEUDO_REGISTER)
	return GENERAL_REGNO_P (regno);
    }
  return 1;
}

/* Return 1 if OP is a register operand that is (or could be) an FR reg.  */

int
fr_register_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  if (! register_operand (op, mode))
    return 0;
  if (GET_CODE (op) == SUBREG)
    op = SUBREG_REG (op);
  if (GET_CODE (op) == REG)
    {
      unsigned int regno = REGNO (op);
      if (regno < FIRST_PSEUDO_REGISTER)
	return FR_REGNO_P (regno);
    }
  return 1;
}

/* Return 1 if OP is a register operand that is (or could be) a GR/FR reg.  */

int
grfr_register_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  if (! register_operand (op, mode))
    return 0;
  if (GET_CODE (op) == SUBREG)
    op = SUBREG_REG (op);
  if (GET_CODE (op) == REG)
    {
      unsigned int regno = REGNO (op);
      if (regno < FIRST_PSEUDO_REGISTER)
	return GENERAL_REGNO_P (regno) || FR_REGNO_P (regno);
    }
  return 1;
}

/* Return 1 if OP is a nonimmediate operand that is (or could be) a GR reg.  */

int
gr_nonimmediate_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  if (! nonimmediate_operand (op, mode))
    return 0;
  if (GET_CODE (op) == SUBREG)
    op = SUBREG_REG (op);
  if (GET_CODE (op) == REG)
    {
      unsigned int regno = REGNO (op);
      if (regno < FIRST_PSEUDO_REGISTER)
	return GENERAL_REGNO_P (regno);
    }
  return 1;
}

/* Return 1 if OP is a nonimmediate operand that is (or could be) a FR reg.  */

int
fr_nonimmediate_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  if (! nonimmediate_operand (op, mode))
    return 0;
  if (GET_CODE (op) == SUBREG)
    op = SUBREG_REG (op);
  if (GET_CODE (op) == REG)
    {
      unsigned int regno = REGNO (op);
      if (regno < FIRST_PSEUDO_REGISTER)
	return FR_REGNO_P (regno);
    }
  return 1;
}

/* Return 1 if OP is a nonimmediate operand that is a GR/FR reg.  */

int
grfr_nonimmediate_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  if (! nonimmediate_operand (op, mode))
    return 0;
  if (GET_CODE (op) == SUBREG)
    op = SUBREG_REG (op);
  if (GET_CODE (op) == REG)
    {
      unsigned int regno = REGNO (op);
      if (regno < FIRST_PSEUDO_REGISTER)
	return GENERAL_REGNO_P (regno) || FR_REGNO_P (regno);
    }
  return 1;
}

/* Return 1 if OP is a GR register operand, or zero.  */

int
gr_reg_or_0_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  return (op == const0_rtx || gr_register_operand (op, mode));
}

/* Return 1 if OP is a GR register operand, or a 5 bit immediate operand.  */

int
gr_reg_or_5bit_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  return ((GET_CODE (op) == CONST_INT && INTVAL (op) >= 0 && INTVAL (op) < 32)
	  || GET_CODE (op) == CONSTANT_P_RTX
	  || gr_register_operand (op, mode));
}

/* Return 1 if OP is a GR register operand, or a 6 bit immediate operand.  */

int
gr_reg_or_6bit_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  return ((GET_CODE (op) == CONST_INT && CONST_OK_FOR_M (INTVAL (op)))
	  || GET_CODE (op) == CONSTANT_P_RTX
	  || gr_register_operand (op, mode));
}

/* Return 1 if OP is a GR register operand, or an 8 bit immediate operand.  */

int
gr_reg_or_8bit_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  return ((GET_CODE (op) == CONST_INT && CONST_OK_FOR_K (INTVAL (op)))
	  || GET_CODE (op) == CONSTANT_P_RTX
	  || gr_register_operand (op, mode));
}

/* Return 1 if OP is a GR/FR register operand, or an 8 bit immediate.  */

int
grfr_reg_or_8bit_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  return ((GET_CODE (op) == CONST_INT && CONST_OK_FOR_K (INTVAL (op)))
	  || GET_CODE (op) == CONSTANT_P_RTX
	  || grfr_register_operand (op, mode));
}

/* Return 1 if OP is a register operand, or an 8 bit adjusted immediate
   operand.  */

int
gr_reg_or_8bit_adjusted_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  return ((GET_CODE (op) == CONST_INT && CONST_OK_FOR_L (INTVAL (op)))
	  || GET_CODE (op) == CONSTANT_P_RTX
	  || gr_register_operand (op, mode));
}

/* Return 1 if OP is a register operand, or is valid for both an 8 bit
   immediate and an 8 bit adjusted immediate operand.  This is necessary
   because when we emit a compare, we don't know what the condition will be,
   so we need the union of the immediates accepted by GT and LT.  */

int
gr_reg_or_8bit_and_adjusted_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  return ((GET_CODE (op) == CONST_INT && CONST_OK_FOR_K (INTVAL (op))
	   && CONST_OK_FOR_L (INTVAL (op)))
	  || GET_CODE (op) == CONSTANT_P_RTX
	  || gr_register_operand (op, mode));
}

/* Return 1 if OP is a register operand, or a 14 bit immediate operand.  */

int
gr_reg_or_14bit_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  return ((GET_CODE (op) == CONST_INT && CONST_OK_FOR_I (INTVAL (op)))
	  || GET_CODE (op) == CONSTANT_P_RTX
	  || gr_register_operand (op, mode));
}

/* Return 1 if OP is a register operand, or a 22 bit immediate operand.  */

int
gr_reg_or_22bit_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  return ((GET_CODE (op) == CONST_INT && CONST_OK_FOR_J (INTVAL (op)))
	  || GET_CODE (op) == CONSTANT_P_RTX
	  || gr_register_operand (op, mode));
}

/* Return 1 if OP is a 6 bit immediate operand.  */

int
shift_count_operand (op, mode)
     rtx op;
     enum machine_mode mode ATTRIBUTE_UNUSED;
{
  return ((GET_CODE (op) == CONST_INT && CONST_OK_FOR_M (INTVAL (op)))
	  || GET_CODE (op) == CONSTANT_P_RTX);
}

/* Return 1 if OP is a 5 bit immediate operand.  */

int
shift_32bit_count_operand (op, mode)
     rtx op;
     enum machine_mode mode ATTRIBUTE_UNUSED;
{
  return ((GET_CODE (op) == CONST_INT
	   && (INTVAL (op) >= 0 && INTVAL (op) < 32))
	  || GET_CODE (op) == CONSTANT_P_RTX);
}

/* Return 1 if OP is a 2, 4, 8, or 16 immediate operand.  */

int
shladd_operand (op, mode)
     rtx op;
     enum machine_mode mode ATTRIBUTE_UNUSED;
{
  return (GET_CODE (op) == CONST_INT
	  && (INTVAL (op) == 2 || INTVAL (op) == 4
	      || INTVAL (op) == 8 || INTVAL (op) == 16));
}

/* Return 1 if OP is a -16, -8, -4, -1, 1, 4, 8, or 16 immediate operand. */

int
fetchadd_operand (op, mode)
     rtx op;
     enum machine_mode mode ATTRIBUTE_UNUSED;
{
  return (GET_CODE (op) == CONST_INT
          && (INTVAL (op) == -16 || INTVAL (op) == -8 ||
              INTVAL (op) == -4  || INTVAL (op) == -1 ||
              INTVAL (op) == 1   || INTVAL (op) == 4  ||
              INTVAL (op) == 8   || INTVAL (op) == 16));
}

/* Return 1 if OP is a floating-point constant zero, one, or a register.  */

int
fr_reg_or_fp01_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  return ((GET_CODE (op) == CONST_DOUBLE && CONST_DOUBLE_OK_FOR_G (op))
	  || fr_register_operand (op, mode));
}

/* Like nonimmediate_operand, but don't allow MEMs that try to use a
   POST_MODIFY with a REG as displacement.  */

int
destination_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  if (! nonimmediate_operand (op, mode))
    return 0;
  if (GET_CODE (op) == MEM
      && GET_CODE (XEXP (op, 0)) == POST_MODIFY
      && GET_CODE (XEXP (XEXP (XEXP (op, 0), 1), 1)) == REG)
    return 0;
  return 1;
}

/* Like memory_operand, but don't allow post-increments.  */

int
not_postinc_memory_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  return (memory_operand (op, mode)
	  && GET_RTX_CLASS (GET_CODE (XEXP (op, 0))) != 'a');
}

/* Return 1 if this is a comparison operator, which accepts an normal 8-bit
   signed immediate operand.  */

int
normal_comparison_operator (op, mode)
    register rtx op;
    enum machine_mode mode;
{
  enum rtx_code code = GET_CODE (op);
  return ((mode == VOIDmode || GET_MODE (op) == mode)
	  && (code == EQ || code == NE
	      || code == GT || code == LE || code == GTU || code == LEU));
}

/* Return 1 if this is a comparison operator, which accepts an adjusted 8-bit
   signed immediate operand.  */

int
adjusted_comparison_operator (op, mode)
    register rtx op;
    enum machine_mode mode;
{
  enum rtx_code code = GET_CODE (op);
  return ((mode == VOIDmode || GET_MODE (op) == mode)
	  && (code == LT || code == GE || code == LTU || code == GEU));
}

/* Return 1 if this is a signed inequality operator.  */

int
signed_inequality_operator (op, mode)
    register rtx op;
    enum machine_mode mode;
{
  enum rtx_code code = GET_CODE (op);
  return ((mode == VOIDmode || GET_MODE (op) == mode)
	  && (code == GE || code == GT
	      || code == LE || code == LT));
}

/* Return 1 if this operator is valid for predication.  */

int
predicate_operator (op, mode)
    register rtx op;
    enum machine_mode mode;
{
  enum rtx_code code = GET_CODE (op);
  return ((GET_MODE (op) == mode || mode == VOIDmode)
	  && (code == EQ || code == NE));
}

/* Return 1 if this is the ar.lc register.  */

int
ar_lc_reg_operand (op, mode)
     register rtx op;
     enum machine_mode mode;
{
  return (GET_MODE (op) == DImode
	  && (mode == DImode || mode == VOIDmode)
	  && GET_CODE (op) == REG
	  && REGNO (op) == AR_LC_REGNUM);
}

/* Return 1 if this is the ar.ccv register.  */

int
ar_ccv_reg_operand (op, mode)
     register rtx op;
     enum machine_mode mode;
{
  return ((GET_MODE (op) == mode || mode == VOIDmode)
	  && GET_CODE (op) == REG
	  && REGNO (op) == AR_CCV_REGNUM);
}

/* Like general_operand, but don't allow (mem (addressof)).  */

int
general_tfmode_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  if (! general_operand (op, mode))
    return 0;
  if (GET_CODE (op) == MEM && GET_CODE (XEXP (op, 0)) == ADDRESSOF)
    return 0;
  return 1;
}

/* Similarly.  */

int
destination_tfmode_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  if (! destination_operand (op, mode))
    return 0;
  if (GET_CODE (op) == MEM && GET_CODE (XEXP (op, 0)) == ADDRESSOF)
    return 0;
  return 1;
}

/* Similarly.  */

int
tfreg_or_fp01_operand (op, mode)
     rtx op;
     enum machine_mode mode;
{
  if (GET_CODE (op) == SUBREG)
    return 0;
  return fr_reg_or_fp01_operand (op, mode);
}

/* Return 1 if the operands of a move are ok.  */

int
ia64_move_ok (dst, src)
     rtx dst, src;
{
  /* If we're under init_recog_no_volatile, we'll not be able to use
     memory_operand.  So check the code directly and don't worry about
     the validity of the underlying address, which should have been
     checked elsewhere anyway.  */
  if (GET_CODE (dst) != MEM)
    return 1;
  if (GET_CODE (src) == MEM)
    return 0;
  if (register_operand (src, VOIDmode))
    return 1;

  /* Otherwise, this must be a constant, and that either 0 or 0.0 or 1.0.  */
  if (INTEGRAL_MODE_P (GET_MODE (dst)))
    return src == const0_rtx;
  else
    return GET_CODE (src) == CONST_DOUBLE && CONST_DOUBLE_OK_FOR_G (src);
}

/* Check if OP is a mask suitible for use with SHIFT in a dep.z instruction.
   Return the length of the field, or <= 0 on failure.  */

int
ia64_depz_field_mask (rop, rshift)
     rtx rop, rshift;
{
  unsigned HOST_WIDE_INT op = INTVAL (rop);
  unsigned HOST_WIDE_INT shift = INTVAL (rshift);

  /* Get rid of the zero bits we're shifting in.  */
  op >>= shift;

  /* We must now have a solid block of 1's at bit 0.  */
  return exact_log2 (op + 1);
}

/* Expand a symbolic constant load.  */
/* ??? Should generalize this, so that we can also support 32 bit pointers.  */

void
ia64_expand_load_address (dest, src, scratch)
      rtx dest, src, scratch;
{
  rtx temp;

  /* The destination could be a MEM during initial rtl generation,
     which isn't a valid destination for the PIC load address patterns.  */
  if (! register_operand (dest, DImode))
    temp = gen_reg_rtx (DImode);
  else
    temp = dest;

  if (TARGET_AUTO_PIC)
    emit_insn (gen_load_gprel64 (temp, src));
  else if (GET_CODE (src) == SYMBOL_REF && SYMBOL_REF_FLAG (src))
    emit_insn (gen_load_fptr (temp, src));
  else if (sdata_symbolic_operand (src, DImode))
    emit_insn (gen_load_gprel (temp, src));
  else if (GET_CODE (src) == CONST
	   && GET_CODE (XEXP (src, 0)) == PLUS
	   && GET_CODE (XEXP (XEXP (src, 0), 1)) == CONST_INT
	   && (INTVAL (XEXP (XEXP (src, 0), 1)) & 0x1fff) != 0)
    {
      rtx subtarget = no_new_pseudos ? temp : gen_reg_rtx (DImode);
      rtx sym = XEXP (XEXP (src, 0), 0);
      HOST_WIDE_INT ofs, hi, lo;

      /* Split the offset into a sign extended 14-bit low part
	 and a complementary high part.  */
      ofs = INTVAL (XEXP (XEXP (src, 0), 1));
      lo = ((ofs & 0x3fff) ^ 0x2000) - 0x2000;
      hi = ofs - lo;

      if (! scratch)
	scratch = no_new_pseudos ? subtarget : gen_reg_rtx (DImode);

      emit_insn (gen_load_symptr (subtarget, plus_constant (sym, hi),
				  scratch));
      emit_insn (gen_adddi3 (temp, subtarget, GEN_INT (lo)));
    }
  else
    {
      rtx insn;
      if (! scratch)
	scratch = no_new_pseudos ? temp : gen_reg_rtx (DImode);

      insn = emit_insn (gen_load_symptr (temp, src, scratch));
      REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_EQUAL, src, REG_NOTES (insn));
    }

  if (temp != dest)
    emit_move_insn (dest, temp);
}

rtx
ia64_gp_save_reg (setjmp_p)
     int setjmp_p;
{
  rtx save = cfun->machine->ia64_gp_save;

  if (save != NULL)
    {
      /* We can't save GP in a pseudo if we are calling setjmp, because
	 pseudos won't be restored by longjmp.  For now, we save it in r4.  */
      /* ??? It would be more efficient to save this directly into a stack
	 slot.  Unfortunately, the stack slot address gets cse'd across
	 the setjmp call because the NOTE_INSN_SETJMP note is in the wrong
	 place.  */

      /* ??? Get the barf bag, Virginia.  We've got to replace this thing
         in place, since this rtx is used in exception handling receivers.
         Moreover, we must get this rtx out of regno_reg_rtx or reload
         will do the wrong thing.  */
      unsigned int old_regno = REGNO (save);
      if (setjmp_p && old_regno != GR_REG (4))
        {
          REGNO (save) = GR_REG (4);
          regno_reg_rtx[old_regno] = gen_rtx_raw_REG (DImode, old_regno);
        }
    }
  else
    {
      if (setjmp_p)
	save = gen_rtx_REG (DImode, GR_REG (4));
      else if (! optimize)
	save = gen_rtx_REG (DImode, LOC_REG (0));
      else
	save = gen_reg_rtx (DImode);
      cfun->machine->ia64_gp_save = save;
    }

  return save;
}

/* Split a post-reload TImode reference into two DImode components.  */

rtx
ia64_split_timode (out, in, scratch)
     rtx out[2];
     rtx in, scratch;
{
  switch (GET_CODE (in))
    {
    case REG:
      out[0] = gen_rtx_REG (DImode, REGNO (in));
      out[1] = gen_rtx_REG (DImode, REGNO (in) + 1);
      return NULL_RTX;

    case MEM:
      {
	rtx base = XEXP (in, 0);

	switch (GET_CODE (base))
	  {
	  case REG:
	    out[0] = change_address (in, DImode, NULL_RTX);
	    break;
	  case POST_MODIFY:
	    base = XEXP (base, 0);
	    out[0] = change_address (in, DImode, NULL_RTX);
	    break;

	  /* Since we're changing the mode, we need to change to POST_MODIFY
	     as well to preserve the size of the increment.  Either that or
	     do the update in two steps, but we've already got this scratch
	     register handy so let's use it.  */
	  case POST_INC:
	    base = XEXP (base, 0);
	    out[0] = change_address (in, DImode,
	      gen_rtx_POST_MODIFY (Pmode, base,plus_constant (base, 16)));
	    break;
	  case POST_DEC:
	    base = XEXP (base, 0);
	    out[0] = change_address (in, DImode,
	      gen_rtx_POST_MODIFY (Pmode, base,plus_constant (base, -16)));
	    break;
	  default:
	    abort ();
	  }

	if (scratch == NULL_RTX)
	  abort ();
	out[1] = change_address (in, DImode, scratch);
	return gen_adddi3 (scratch, base, GEN_INT (8));
      }

    case CONST_INT:
    case CONST_DOUBLE:
      split_double (in, &out[0], &out[1]);
      return NULL_RTX;

    default:
      abort ();
    }
}

/* ??? Fixing GR->FR TFmode moves during reload is hard.  You need to go
   through memory plus an extra GR scratch register.  Except that you can
   either get the first from SECONDARY_MEMORY_NEEDED or the second from
   SECONDARY_RELOAD_CLASS, but not both.

   We got into problems in the first place by allowing a construct like
   (subreg:TF (reg:TI)), which we got from a union containing a long double.  
   This solution attempts to prevent this situation from ocurring.  When
   we see something like the above, we spill the inner register to memory.  */

rtx
spill_tfmode_operand (in, force)
     rtx in;
     int force;
{
  if (GET_CODE (in) == SUBREG
      && GET_MODE (SUBREG_REG (in)) == TImode
      && GET_CODE (SUBREG_REG (in)) == REG)
    {
      rtx mem = gen_mem_addressof (SUBREG_REG (in), NULL_TREE);
      return gen_rtx_MEM (TFmode, copy_to_reg (XEXP (mem, 0)));
    }
  else if (force && GET_CODE (in) == REG)
    {
      rtx mem = gen_mem_addressof (in, NULL_TREE);
      return gen_rtx_MEM (TFmode, copy_to_reg (XEXP (mem, 0)));
    }
  else if (GET_CODE (in) == MEM
	   && GET_CODE (XEXP (in, 0)) == ADDRESSOF)
    {
      return change_address (in, TFmode, copy_to_reg (XEXP (in, 0)));
    }
  else
    return in;
}

/* Emit comparison instruction if necessary, returning the expression
   that holds the compare result in the proper mode.  */

rtx
ia64_expand_compare (code, mode)
     enum rtx_code code;
     enum machine_mode mode;
{
  rtx op0 = ia64_compare_op0, op1 = ia64_compare_op1;
  rtx cmp;

  /* If we have a BImode input, then we already have a compare result, and
     do not need to emit another comparison.  */
  if (GET_MODE (op0) == BImode)
    {
      if ((code == NE || code == EQ) && op1 == const0_rtx)
	cmp = op0;
      else
	abort ();
    }
  else
    {
      cmp = gen_reg_rtx (BImode);
      emit_insn (gen_rtx_SET (VOIDmode, cmp,
			      gen_rtx_fmt_ee (code, BImode, op0, op1)));
      code = NE;
    }

  return gen_rtx_fmt_ee (code, mode, cmp, const0_rtx);
}

/* Emit the appropriate sequence for a call.  */

void
ia64_expand_call (retval, addr, nextarg, sibcall_p)
     rtx retval;
     rtx addr;
     rtx nextarg;
     int sibcall_p;
{
  rtx insn, b0, gp_save, narg_rtx;
  int narg;

  addr = XEXP (addr, 0);
  b0 = gen_rtx_REG (DImode, R_BR (0));

  if (! nextarg)
    narg = 0;
  else if (IN_REGNO_P (REGNO (nextarg)))
    narg = REGNO (nextarg) - IN_REG (0);
  else
    narg = REGNO (nextarg) - OUT_REG (0);
  narg_rtx = GEN_INT (narg);

  if (TARGET_NO_PIC || TARGET_AUTO_PIC)
    {
      if (sibcall_p)
	insn = gen_sibcall_nopic (addr, narg_rtx, b0);
      else if (! retval)
	insn = gen_call_nopic (addr, narg_rtx, b0);
      else
	insn = gen_call_value_nopic (retval, addr, narg_rtx, b0);
      emit_call_insn (insn);
      return;
    }

  if (sibcall_p)
    gp_save = NULL_RTX;
  else
    gp_save = ia64_gp_save_reg (setjmp_operand (addr, VOIDmode));

  /* If this is an indirect call, then we have the address of a descriptor.  */
  if (! symbolic_operand (addr, VOIDmode))
    {
      rtx dest;

      if (! sibcall_p)
	emit_move_insn (gp_save, pic_offset_table_rtx);

      dest = force_reg (DImode, gen_rtx_MEM (DImode, addr));
      emit_move_insn (pic_offset_table_rtx,
		      gen_rtx_MEM (DImode, plus_constant (addr, 8)));

      if (sibcall_p)
	insn = gen_sibcall_pic (dest, narg_rtx, b0);
      else if (! retval)
	insn = gen_call_pic (dest, narg_rtx, b0);
      else
	insn = gen_call_value_pic (retval, dest, narg_rtx, b0);
      emit_call_insn (insn);

      if (! sibcall_p)
	emit_move_insn (pic_offset_table_rtx, gp_save);
    }
  else if (TARGET_CONST_GP)
    {
      if (sibcall_p)
	insn = gen_sibcall_nopic (addr, narg_rtx, b0);
      else if (! retval)
	insn = gen_call_nopic (addr, narg_rtx, b0);
      else
	insn = gen_call_value_nopic (retval, addr, narg_rtx, b0);
      emit_call_insn (insn);
    }
  else
    {
      if (sibcall_p)
	emit_call_insn (gen_sibcall_pic (addr, narg_rtx, b0));
      else
	{
	  emit_move_insn (gp_save, pic_offset_table_rtx);

	  if (! retval)
	    insn = gen_call_pic (addr, narg_rtx, b0);
	  else
	    insn = gen_call_value_pic (retval, addr, narg_rtx, b0);
	  emit_call_insn (insn);

	  emit_move_insn (pic_offset_table_rtx, gp_save);
	}
    }
}

/* Begin the assembly file.  */

void
emit_safe_across_calls (f)
     FILE *f;
{
  unsigned int rs, re;
  int out_state;

  rs = 1;
  out_state = 0;
  while (1)
    {
      while (rs < 64 && call_used_regs[PR_REG (rs)])
	rs++;
      if (rs >= 64)
	break;
      for (re = rs + 1; re < 64 && ! call_used_regs[PR_REG (re)]; re++)
	continue;
      if (out_state == 0)
	{
	  fputs ("\t.pred.safe_across_calls ", f);
	  out_state = 1;
	}
      else
	fputc (',', f);
      if (re == rs + 1)
	fprintf (f, "p%u", rs);
      else
	fprintf (f, "p%u-p%u", rs, re - 1);
      rs = re + 1;
    }
  if (out_state)
    fputc ('\n', f);
}


/* Structure to be filled in by ia64_compute_frame_size with register
   save masks and offsets for the current function.  */

struct ia64_frame_info
{
  HOST_WIDE_INT total_size;	/* size of the stack frame, not including
				   the caller's scratch area.  */
  HOST_WIDE_INT spill_cfa_off;	/* top of the reg spill area from the cfa.  */
  HOST_WIDE_INT spill_size;	/* size of the gr/br/fr spill area.  */
  HOST_WIDE_INT extra_spill_size;  /* size of spill area for others.  */
  HARD_REG_SET mask;		/* mask of saved registers.  */
  unsigned int gr_used_mask;	/* mask of registers in use as gr spill 
				   registers or long-term scratches.  */
  int n_spilled;		/* number of spilled registers.  */
  int reg_fp;			/* register for fp.  */
  int reg_save_b0;		/* save register for b0.  */
  int reg_save_pr;		/* save register for prs.  */
  int reg_save_ar_pfs;		/* save register for ar.pfs.  */
  int reg_save_ar_unat;		/* save register for ar.unat.  */
  int reg_save_ar_lc;		/* save register for ar.lc.  */
  int n_input_regs;		/* number of input registers used.  */
  int n_local_regs;		/* number of local registers used.  */
  int n_output_regs;		/* number of output registers used.  */
  int n_rotate_regs;		/* number of rotating registers used.  */

  char need_regstk;		/* true if a .regstk directive needed.  */
  char initialized;		/* true if the data is finalized.  */
};

/* Current frame information calculated by ia64_compute_frame_size.  */
static struct ia64_frame_info current_frame_info;

/* Helper function for ia64_compute_frame_size: find an appropriate general
   register to spill some special register to.  SPECIAL_SPILL_MASK contains
   bits in GR0 to GR31 that have already been allocated by this routine.
   TRY_LOCALS is true if we should attempt to locate a local regnum.  */

static int
find_gr_spill (try_locals)
     int try_locals;
{
  int regno;

  /* If this is a leaf function, first try an otherwise unused
     call-clobbered register.  */
  if (current_function_is_leaf)
    {
      for (regno = GR_REG (1); regno <= GR_REG (31); regno++)
	if (! regs_ever_live[regno]
	    && call_used_regs[regno]
	    && ! fixed_regs[regno]
	    && ! global_regs[regno]
	    && ((current_frame_info.gr_used_mask >> regno) & 1) == 0)
	  {
	    current_frame_info.gr_used_mask |= 1 << regno;
	    return regno;
	  }
    }

  if (try_locals)
    {
      regno = current_frame_info.n_local_regs;
      /* If there is a frame pointer, then we can't use loc79, because
	 that is HARD_FRAME_POINTER_REGNUM.  In particular, see the
	 reg_name switching code in ia64_expand_prologue.  */
      if (regno < (80 - frame_pointer_needed))
	{
	  current_frame_info.n_local_regs = regno + 1;
	  return LOC_REG (0) + regno;
	}
    }

  /* Failed to find a general register to spill to.  Must use stack.  */
  return 0;
}

/* In order to make for nice schedules, we try to allocate every temporary
   to a different register.  We must of course stay away from call-saved,
   fixed, and global registers.  We must also stay away from registers
   allocated in current_frame_info.gr_used_mask, since those include regs
   used all through the prologue.

   Any register allocated here must be used immediately.  The idea is to
   aid scheduling, not to solve data flow problems.  */

static int last_scratch_gr_reg;

static int
next_scratch_gr_reg ()
{
  int i, regno;

  for (i = 0; i < 32; ++i)
    {
      regno = (last_scratch_gr_reg + i + 1) & 31;
      if (call_used_regs[regno]
	  && ! fixed_regs[regno]
	  && ! global_regs[regno]
	  && ((current_frame_info.gr_used_mask >> regno) & 1) == 0)
	{
	  last_scratch_gr_reg = regno;
	  return regno;
	}
    }

  /* There must be _something_ available.  */
  abort ();
}

/* Helper function for ia64_compute_frame_size, called through
   diddle_return_value.  Mark REG in current_frame_info.gr_used_mask.  */

static void
mark_reg_gr_used_mask (reg, data)
     rtx reg;
     void *data ATTRIBUTE_UNUSED;
{
  unsigned int regno = REGNO (reg);
  if (regno < 32)
    current_frame_info.gr_used_mask |= 1 << regno;
}

/* 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.  */

static void
ia64_compute_frame_size (size)
     HOST_WIDE_INT size;
{
  HOST_WIDE_INT total_size;
  HOST_WIDE_INT spill_size = 0;
  HOST_WIDE_INT extra_spill_size = 0;
  HOST_WIDE_INT pretend_args_size;
  HARD_REG_SET mask;
  int n_spilled = 0;
  int spilled_gr_p = 0;
  int spilled_fr_p = 0;
  unsigned int regno;
  int i;

  if (current_frame_info.initialized)
    return;

  memset (&current_frame_info, 0, sizeof current_frame_info);
  CLEAR_HARD_REG_SET (mask);

  /* Don't allocate scratches to the return register.  */
  diddle_return_value (mark_reg_gr_used_mask, NULL);

  /* Don't allocate scratches to the EH scratch registers.  */
  if (cfun->machine->ia64_eh_epilogue_sp)
    mark_reg_gr_used_mask (cfun->machine->ia64_eh_epilogue_sp, NULL);
  if (cfun->machine->ia64_eh_epilogue_bsp)
    mark_reg_gr_used_mask (cfun->machine->ia64_eh_epilogue_bsp, NULL);

  /* Find the size of the register stack frame.  We have only 80 local
     registers, because we reserve 8 for the inputs and 8 for the
     outputs.  */

  /* Skip HARD_FRAME_POINTER_REGNUM (loc79) when frame_pointer_needed,
     since we'll be adjusting that down later.  */
  regno = LOC_REG (78) + ! frame_pointer_needed;
  for (; regno >= LOC_REG (0); regno--)
    if (regs_ever_live[regno])
      break;
  current_frame_info.n_local_regs = regno - LOC_REG (0) + 1;

  /* For functions marked with the syscall_linkage attribute, we must mark
     all eight input registers as in use, so that locals aren't visible to
     the caller.  */

  if (cfun->machine->n_varargs > 0
      || lookup_attribute ("syscall_linkage",
			   TYPE_ATTRIBUTES (TREE_TYPE (current_function_decl))))
    current_frame_info.n_input_regs = 8;
  else
    {
      for (regno = IN_REG (7); regno >= IN_REG (0); regno--)
	if (regs_ever_live[regno])
	  break;
      current_frame_info.n_input_regs = regno - IN_REG (0) + 1;
    }

  for (regno = OUT_REG (7); regno >= OUT_REG (0); regno--)
    if (regs_ever_live[regno])
      break;
  i = regno - OUT_REG (0) + 1;

  /* When -p profiling, we need one output register for the mcount argument.
     Likwise for -a profiling for the bb_init_func argument.  For -ax
     profiling, we need two output registers for the two bb_init_trace_func
     arguments.  */
  if (profile_flag || profile_block_flag == 1)
    i = MAX (i, 1);
  else if (profile_block_flag == 2)
    i = MAX (i, 2);
  current_frame_info.n_output_regs = i;

  /* ??? No rotating register support yet.  */
  current_frame_info.n_rotate_regs = 0;

  /* Discover which registers need spilling, and how much room that
     will take.  Begin with floating point and general registers, 
     which will always wind up on the stack.  */

  for (regno = FR_REG (2); regno <= FR_REG (127); regno++)
    if (regs_ever_live[regno] && ! call_used_regs[regno])
      {
	SET_HARD_REG_BIT (mask, regno);
	spill_size += 16;
	n_spilled += 1;
	spilled_fr_p = 1;
      }

  for (regno = GR_REG (1); regno <= GR_REG (31); regno++)
    if (regs_ever_live[regno] && ! call_used_regs[regno])
      {
	SET_HARD_REG_BIT (mask, regno);
	spill_size += 8;
	n_spilled += 1;
	spilled_gr_p = 1;
      }

  for (regno = BR_REG (1); regno <= BR_REG (7); regno++)
    if (regs_ever_live[regno] && ! call_used_regs[regno])
      {
	SET_HARD_REG_BIT (mask, regno);
	spill_size += 8;
	n_spilled += 1;
      }

  /* Now come all special registers that might get saved in other
     general registers.  */
  
  if (frame_pointer_needed)
    {
      current_frame_info.reg_fp = find_gr_spill (1);
      /* If we did not get a register, then we take LOC79.  This is guaranteed
	 to be free, even if regs_ever_live is already set, because this is
	 HARD_FRAME_POINTER_REGNUM.  This requires incrementing n_local_regs,
	 as we don't count loc79 above.  */
      if (current_frame_info.reg_fp == 0)
	{
	  current_frame_info.reg_fp = LOC_REG (79);
	  current_frame_info.n_local_regs++;
	}
    }

  if (! current_function_is_leaf)
    {
      /* Emit a save of BR0 if we call other functions.  Do this even
	 if this function doesn't return, as EH depends on this to be
	 able to unwind the stack.  */
      SET_HARD_REG_BIT (mask, BR_REG (0));

      current_frame_info.reg_save_b0 = find_gr_spill (1);
      if (current_frame_info.reg_save_b0 == 0)
	{
	  spill_size += 8;
	  n_spilled += 1;
	}

      /* Similarly for ar.pfs.  */
      SET_HARD_REG_BIT (mask, AR_PFS_REGNUM);
      current_frame_info.reg_save_ar_pfs = find_gr_spill (1);
      if (current_frame_info.reg_save_ar_pfs == 0)
	{
	  extra_spill_size += 8;
	  n_spilled += 1;
	}
    }
  else
    {
      if (regs_ever_live[BR_REG (0)] && ! call_used_regs[BR_REG (0)])
	{
	  SET_HARD_REG_BIT (mask, BR_REG (0));
	  spill_size += 8;
	  n_spilled += 1;
	}
    }

  /* Unwind descriptor hackery: things are most efficient if we allocate
     consecutive GR save registers for RP, PFS, FP in that order. However,
     it is absolutely critical that FP get the only hard register that's
     guaranteed to be free, so we allocated it first.  If all three did
     happen to be allocated hard regs, and are consecutive, rearrange them
     into the preferred order now.  */
  if (current_frame_info.reg_fp != 0
      && current_frame_info.reg_save_b0 == current_frame_info.reg_fp + 1
      && current_frame_info.reg_save_ar_pfs == current_frame_info.reg_fp + 2)
    {
      current_frame_info.reg_save_b0 = current_frame_info.reg_fp;
      current_frame_info.reg_save_ar_pfs = current_frame_info.reg_fp + 1;
      current_frame_info.reg_fp = current_frame_info.reg_fp + 2;
    }

  /* See if we need to store the predicate register block.  */
  for (regno = PR_REG (0); regno <= PR_REG (63); regno++)
    if (regs_ever_live[regno] && ! call_used_regs[regno])
      break;
  if (regno <= PR_REG (63))
    {
      SET_HARD_REG_BIT (mask, PR_REG (0));
      current_frame_info.reg_save_pr = find_gr_spill (1);
      if (current_frame_info.reg_save_pr == 0)
	{
	  extra_spill_size += 8;
	  n_spilled += 1;
	}

      /* ??? Mark them all as used so that register renaming and such
	 are free to use them.  */
      for (regno = PR_REG (0); regno <= PR_REG (63); regno++)
	regs_ever_live[regno] = 1;
    }

  /* If we're forced to use st8.spill, we're forced to save and restore
     ar.unat as well.  */
  if (spilled_gr_p || cfun->machine->n_varargs)
    {
      SET_HARD_REG_BIT (mask, AR_UNAT_REGNUM);
      current_frame_info.reg_save_ar_unat = find_gr_spill (spill_size == 0);
      if (current_frame_info.reg_save_ar_unat == 0)
	{
	  extra_spill_size += 8;
	  n_spilled += 1;
	}
    }

  if (regs_ever_live[AR_LC_REGNUM])
    {
      SET_HARD_REG_BIT (mask, AR_LC_REGNUM);
      current_frame_info.reg_save_ar_lc = find_gr_spill (spill_size == 0);
      if (current_frame_info.reg_save_ar_lc == 0)
	{
	  extra_spill_size += 8;
	  n_spilled += 1;
	}
    }

  /* If we have an odd number of words of pretend arguments written to
     the stack, then the FR save area will be unaligned.  We round the
     size of this area up to keep things 16 byte aligned.  */
  if (spilled_fr_p)
    pretend_args_size = IA64_STACK_ALIGN (current_function_pretend_args_size);
  else
    pretend_args_size = current_function_pretend_args_size;

  total_size = (spill_size + extra_spill_size + size + pretend_args_size
		+ current_function_outgoing_args_size);
  total_size = IA64_STACK_ALIGN (total_size);

  /* We always use the 16-byte scratch area provided by the caller, but
     if we are a leaf function, there's no one to which we need to provide
     a scratch area.  */
  if (current_function_is_leaf)
    total_size = MAX (0, total_size - 16);

  current_frame_info.total_size = total_size;
  current_frame_info.spill_cfa_off = pretend_args_size - 16;
  current_frame_info.spill_size = spill_size;
  current_frame_info.extra_spill_size = extra_spill_size;
  COPY_HARD_REG_SET (current_frame_info.mask, mask);
  current_frame_info.n_spilled = n_spilled;
  current_frame_info.initialized = reload_completed;
}

/* Compute the initial difference between the specified pair of registers.  */

HOST_WIDE_INT
ia64_initial_elimination_offset (from, to)
     int from, to;
{
  HOST_WIDE_INT offset;

  ia64_compute_frame_size (get_frame_size ());
  switch (from)
    {
    case FRAME_POINTER_REGNUM:
      if (to == HARD_FRAME_POINTER_REGNUM)
	{
	  if (current_function_is_leaf)
	    offset = -current_frame_info.total_size;
	  else
	    offset = -(current_frame_info.total_size
		       - current_function_outgoing_args_size - 16);
	}
      else if (to == STACK_POINTER_REGNUM)
	{
	  if (current_function_is_leaf)
	    offset = 0;
	  else
	    offset = 16 + current_function_outgoing_args_size;
	}
      else
	abort ();
      break;

    case ARG_POINTER_REGNUM:
      /* Arguments start above the 16 byte save area, unless stdarg
	 in which case we store through the 16 byte save area.  */
      if (to == HARD_FRAME_POINTER_REGNUM)
	offset = 16 - current_function_pretend_args_size;
      else if (to == STACK_POINTER_REGNUM)
	offset = (current_frame_info.total_size
		  + 16 - current_function_pretend_args_size);
      else
	abort ();
      break;

    case RETURN_ADDRESS_POINTER_REGNUM:
      offset = 0;
      break;

    default:
      abort ();
    }

  return offset;
}

/* If there are more than a trivial number of register spills, we use
   two interleaved iterators so that we can get two memory references
   per insn group.

   In order to simplify things in the prologue and epilogue expanders,
   we use helper functions to fix up the memory references after the
   fact with the appropriate offsets to a POST_MODIFY memory mode.
   The following data structure tracks the state of the two iterators
   while insns are being emitted.  */

struct spill_fill_data
{
  rtx init_after;		/* point at which to emit intializations */
  rtx init_reg[2];		/* initial base register */
  rtx iter_reg[2];		/* the iterator registers */
  rtx *prev_addr[2];		/* address of last memory use */
  HOST_WIDE_INT prev_off[2];	/* last offset */
  int n_iter;			/* number of iterators in use */
  int next_iter;		/* next iterator to use */
  unsigned int save_gr_used_mask;
};

static struct spill_fill_data spill_fill_data;

static void
setup_spill_pointers (n_spills, init_reg, cfa_off)
     int n_spills;
     rtx init_reg;
     HOST_WIDE_INT cfa_off;
{
  int i;

  spill_fill_data.init_after = get_last_insn ();
  spill_fill_data.init_reg[0] = init_reg;
  spill_fill_data.init_reg[1] = init_reg;
  spill_fill_data.prev_addr[0] = NULL;
  spill_fill_data.prev_addr[1] = NULL;
  spill_fill_data.prev_off[0] = cfa_off;
  spill_fill_data.prev_off[1] = cfa_off;
  spill_fill_data.next_iter = 0;
  spill_fill_data.save_gr_used_mask = current_frame_info.gr_used_mask;

  spill_fill_data.n_iter = 1 + (n_spills > 2);
  for (i = 0; i < spill_fill_data.n_iter; ++i)
    {
      int regno = next_scratch_gr_reg ();
      spill_fill_data.iter_reg[i] = gen_rtx_REG (DImode, regno);
      current_frame_info.gr_used_mask |= 1 << regno;
    }
}

static void
finish_spill_pointers ()
{
  current_frame_info.gr_used_mask = spill_fill_data.save_gr_used_mask;
}

static rtx
spill_restore_mem (reg, cfa_off)
     rtx reg;
     HOST_WIDE_INT cfa_off;
{
  int iter = spill_fill_data.next_iter;
  HOST_WIDE_INT disp = spill_fill_data.prev_off[iter] - cfa_off;
  rtx disp_rtx = GEN_INT (disp);
  rtx mem;

  if (spill_fill_data.prev_addr[iter])
    {
      if (CONST_OK_FOR_N (disp))
	*spill_fill_data.prev_addr[iter]
	  = gen_rtx_POST_MODIFY (DImode, spill_fill_data.iter_reg[iter],
				 gen_rtx_PLUS (DImode,
					       spill_fill_data.iter_reg[iter],
					       disp_rtx));
      else
	{
	  /* ??? Could use register post_modify for loads.  */
	  if (! CONST_OK_FOR_I (disp))
	    {
	      rtx tmp = gen_rtx_REG (DImode, next_scratch_gr_reg ());
	      emit_move_insn (tmp, disp_rtx);
	      disp_rtx = tmp;
	    }
	  emit_insn (gen_adddi3 (spill_fill_data.iter_reg[iter],
				 spill_fill_data.iter_reg[iter], disp_rtx));
	}
    }
  /* Micro-optimization: if we've created a frame pointer, it's at
     CFA 0, which may allow the real iterator to be initialized lower,
     slightly increasing parallelism.  Also, if there are few saves
     it may eliminate the iterator entirely.  */
  else if (disp == 0
	   && spill_fill_data.init_reg[iter] == stack_pointer_rtx
	   && frame_pointer_needed)
    {
      mem = gen_rtx_MEM (GET_MODE (reg), hard_frame_pointer_rtx);
      MEM_ALIAS_SET (mem) = get_varargs_alias_set ();
      return mem;
    }
  else
    {
      rtx seq;

      if (disp == 0)
	seq = gen_movdi (spill_fill_data.iter_reg[iter],
			 spill_fill_data.init_reg[iter]);
      else
	{
	  start_sequence ();

	  if (! CONST_OK_FOR_I (disp))
	    {
	      rtx tmp = gen_rtx_REG (DImode, next_scratch_gr_reg ());
	      emit_move_insn (tmp, disp_rtx);
	      disp_rtx = tmp;
	    }

	  emit_insn (gen_adddi3 (spill_fill_data.iter_reg[iter],
				 spill_fill_data.init_reg[iter],
				 disp_rtx));

	  seq = gen_sequence ();
	  end_sequence ();
	}

      /* Careful for being the first insn in a sequence.  */
      if (spill_fill_data.init_after)
	spill_fill_data.init_after
	  = emit_insn_after (seq, spill_fill_data.init_after);
      else
	{
	  rtx first = get_insns ();
	  if (first)
	    spill_fill_data.init_after
	      = emit_insn_before (seq, first);
	  else
	    spill_fill_data.init_after = emit_insn (seq);
	}
    }

  mem = gen_rtx_MEM (GET_MODE (reg), spill_fill_data.iter_reg[iter]);

  /* ??? Not all of the spills are for varargs, but some of them are.
     The rest of the spills belong in an alias set of their own.  But
     it doesn't actually hurt to include them here.  */
  MEM_ALIAS_SET (mem) = get_varargs_alias_set ();

  spill_fill_data.prev_addr[iter] = &XEXP (mem, 0);
  spill_fill_data.prev_off[iter] = cfa_off;

  if (++iter >= spill_fill_data.n_iter)
    iter = 0;
  spill_fill_data.next_iter = iter;

  return mem;
}

static void
do_spill (move_fn, reg, cfa_off, frame_reg)
     rtx (*move_fn) PARAMS ((rtx, rtx, rtx));
     rtx reg, frame_reg;
     HOST_WIDE_INT cfa_off;
{
  rtx mem, insn;

  mem = spill_restore_mem (reg, cfa_off);
  insn = emit_insn ((*move_fn) (mem, reg, GEN_INT (cfa_off)));

  if (frame_reg)
    {
      rtx base;
      HOST_WIDE_INT off;

      RTX_FRAME_RELATED_P (insn) = 1;

      /* Don't even pretend that the unwind code can intuit its way 
	 through a pair of interleaved post_modify iterators.  Just
	 provide the correct answer.  */

      if (frame_pointer_needed)
	{
	  base = hard_frame_pointer_rtx;
	  off = - cfa_off;
	}
      else
	{
	  base = stack_pointer_rtx;
	  off = current_frame_info.total_size - cfa_off;
	}

      REG_NOTES (insn)
	= gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
		gen_rtx_SET (VOIDmode,
			     gen_rtx_MEM (GET_MODE (reg),
					  plus_constant (base, off)),
			     frame_reg),
		REG_NOTES (insn));
    }
}

static void
do_restore (move_fn, reg, cfa_off)
     rtx (*move_fn) PARAMS ((rtx, rtx, rtx));
     rtx reg;
     HOST_WIDE_INT cfa_off;
{
  emit_insn ((*move_fn) (reg, spill_restore_mem (reg, cfa_off),
			 GEN_INT (cfa_off)));
}

/* Wrapper functions that discards the CONST_INT spill offset.  These
   exist so that we can give gr_spill/gr_fill the offset they need and
   use a consistant function interface.  */

static rtx
gen_movdi_x (dest, src, offset)
     rtx dest, src;
     rtx offset ATTRIBUTE_UNUSED;
{
  return gen_movdi (dest, src);
}

static rtx
gen_fr_spill_x (dest, src, offset)
     rtx dest, src;
     rtx offset ATTRIBUTE_UNUSED;
{
  return gen_fr_spill (dest, src);
}

static rtx
gen_fr_restore_x (dest, src, offset)
     rtx dest, src;
     rtx offset ATTRIBUTE_UNUSED;
{
  return gen_fr_restore (dest, src);
}

/* Called after register allocation to add any instructions needed for the
   prologue.  Using a prologue insn is favored compared to putting all of the
   instructions in the FUNCTION_PROLOGUE macro, since it allows the scheduler
   to intermix instructions with the saves of the caller saved registers.  In
   some cases, it might be necessary to emit a barrier instruction as the last
   insn to prevent such scheduling.

   Also any insns generated here should have RTX_FRAME_RELATED_P(insn) = 1
   so that the debug info generation code can handle them properly.

   The register save area is layed out like so:
   cfa+16
	[ varargs spill area ]
	[ fr register spill area ]
	[ br register spill area ]
	[ ar register spill area ]
	[ pr register spill area ]
	[ gr register spill area ] */

/* ??? Get inefficient code when the frame size is larger than can fit in an
   adds instruction.  */

void
ia64_expand_prologue ()
{
  rtx insn, ar_pfs_save_reg, ar_unat_save_reg;
  int i, epilogue_p, regno, alt_regno, cfa_off, n_varargs;
  rtx reg, alt_reg;

  ia64_compute_frame_size (get_frame_size ());
  last_scratch_gr_reg = 15;

  /* If there is no epilogue, then we don't need some prologue insns.
     We need to avoid emitting the dead prologue insns, because flow
     will complain about them.  */
  if (optimize)
    {
      edge e;

      for (e = EXIT_BLOCK_PTR->pred; e ; e = e->pred_next)
	if ((e->flags & EDGE_FAKE) == 0
	    && (e->flags & EDGE_FALLTHRU) != 0)
	  break;
      epilogue_p = (e != NULL);
    }
  else
    epilogue_p = 1;

  /* Set the local, input, and output register names.  We need to do this
     for GNU libc, which creates crti.S/crtn.S by splitting initfini.c in
     half.  If we use in/loc/out register names, then we get assembler errors
     in crtn.S because there is no alloc insn or regstk directive in there.  */
  if (! TARGET_REG_NAMES)
    {
      int inputs = current_frame_info.n_input_regs;
      int locals = current_frame_info.n_local_regs;
      int outputs = current_frame_info.n_output_regs;

      for (i = 0; i < inputs; i++)
	reg_names[IN_REG (i)] = ia64_reg_numbers[i];
      for (i = 0; i < locals; i++)
	reg_names[LOC_REG (i)] = ia64_reg_numbers[inputs + i];
      for (i = 0; i < outputs; i++)
	reg_names[OUT_REG (i)] = ia64_reg_numbers[inputs + locals + i];
    }

  /* Set the frame pointer register name.  The regnum is logically loc79,
     but of course we'll not have allocated that many locals.  Rather than
     worrying about renumbering the existing rtxs, we adjust the name.  */
  /* ??? This code means that we can never use one local register when
     there is a frame pointer.  loc79 gets wasted in this case, as it is
     renamed to a register that will never be used.  See also the try_locals
     code in find_gr_spill.  */
  if (current_frame_info.reg_fp)
    {
      const char *tmp = reg_names[HARD_FRAME_POINTER_REGNUM];
      reg_names[HARD_FRAME_POINTER_REGNUM]
	= reg_names[current_frame_info.reg_fp];
      reg_names[current_frame_info.reg_fp] = tmp;
    }

  /* Fix up the return address placeholder.  */
  /* ??? We can fail if __builtin_return_address is used, and we didn't
     allocate a register in which to save b0.  I can't think of a way to
     eliminate RETURN_ADDRESS_POINTER_REGNUM to a local register and
     then be sure that I got the right one.  Further, reload doesn't seem
     to care if an eliminable register isn't used, and "eliminates" it
     anyway.  */
  if (regs_ever_live[RETURN_ADDRESS_POINTER_REGNUM]
      && current_frame_info.reg_save_b0 != 0)
    XINT (return_address_pointer_rtx, 0) = current_frame_info.reg_save_b0;

  /* We don't need an alloc instruction if we've used no outputs or locals.  */
  if (current_frame_info.n_local_regs == 0
      && current_frame_info.n_output_regs == 0
      && current_frame_info.n_input_regs <= current_function_args_info.words)
    {
      /* If there is no alloc, but there are input registers used, then we
	 need a .regstk directive.  */
      current_frame_info.need_regstk = (TARGET_REG_NAMES != 0);
      ar_pfs_save_reg = NULL_RTX;
    }
  else
    {
      current_frame_info.need_regstk = 0;

      if (current_frame_info.reg_save_ar_pfs)
	regno = current_frame_info.reg_save_ar_pfs;
      else
	regno = next_scratch_gr_reg ();
      ar_pfs_save_reg = gen_rtx_REG (DImode, regno);

      insn = emit_insn (gen_alloc (ar_pfs_save_reg, 
				   GEN_INT (current_frame_info.n_input_regs),
				   GEN_INT (current_frame_info.n_local_regs),
				   GEN_INT (current_frame_info.n_output_regs),
				   GEN_INT (current_frame_info.n_rotate_regs)));
      RTX_FRAME_RELATED_P (insn) = (current_frame_info.reg_save_ar_pfs != 0);
    }

  /* Set up frame pointer, stack pointer, and spill iterators.  */

  n_varargs = cfun->machine->n_varargs;
  setup_spill_pointers (current_frame_info.n_spilled + n_varargs,
			stack_pointer_rtx, 0);

  if (frame_pointer_needed)
    {
      insn = emit_move_insn (hard_frame_pointer_rtx, stack_pointer_rtx);
      RTX_FRAME_RELATED_P (insn) = 1;
    }

  if (current_frame_info.total_size != 0)
    {
      rtx frame_size_rtx = GEN_INT (- current_frame_info.total_size);
      rtx offset;

      if (CONST_OK_FOR_I (- current_frame_info.total_size))
	offset = frame_size_rtx;
      else
	{
	  regno = next_scratch_gr_reg ();
 	  offset = gen_rtx_REG (DImode, regno);
	  emit_move_insn (offset, frame_size_rtx);
	}

      insn = emit_insn (gen_adddi3 (stack_pointer_rtx,
				    stack_pointer_rtx, offset));

      if (! frame_pointer_needed)
	{
	  RTX_FRAME_RELATED_P (insn) = 1;
	  if (GET_CODE (offset) != CONST_INT)
	    {
	      REG_NOTES (insn)
		= gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
			gen_rtx_SET (VOIDmode,
				     stack_pointer_rtx,
				     gen_rtx_PLUS (DImode,
						   stack_pointer_rtx,
						   frame_size_rtx)),
			REG_NOTES (insn));
	    }
	}

      /* ??? At this point we must generate a magic insn that appears to
	 modify the stack pointer, the frame pointer, and all spill
	 iterators.  This would allow the most scheduling freedom.  For
	 now, just hard stop.  */
      emit_insn (gen_blockage ());
    }

  /* Must copy out ar.unat before doing any integer spills.  */
  if (TEST_HARD_REG_BIT (current_frame_info.mask, AR_UNAT_REGNUM))
    {
      if (current_frame_info.reg_save_ar_unat)
	ar_unat_save_reg
	  = gen_rtx_REG (DImode, current_frame_info.reg_save_ar_unat);
      else
	{
	  alt_regno = next_scratch_gr_reg ();
	  ar_unat_save_reg = gen_rtx_REG (DImode, alt_regno);
	  current_frame_info.gr_used_mask |= 1 << alt_regno;
	}

      reg = gen_rtx_REG (DImode, AR_UNAT_REGNUM);
      insn = emit_move_insn (ar_unat_save_reg, reg);
      RTX_FRAME_RELATED_P (insn) = (current_frame_info.reg_save_ar_unat != 0);

      /* Even if we're not going to generate an epilogue, we still
	 need to save the register so that EH works.  */
      if (! epilogue_p && current_frame_info.reg_save_ar_unat)
	emit_insn (gen_rtx_USE (VOIDmode, ar_unat_save_reg));
    }
  else
    ar_unat_save_reg = NULL_RTX;

  /* Spill all varargs registers.  Do this before spilling any GR registers,
     since we want the UNAT bits for the GR registers to override the UNAT
     bits from varargs, which we don't care about.  */

  cfa_off = -16;
  for (regno = GR_ARG_FIRST + 7; n_varargs > 0; --n_varargs, --regno)
    {
      reg = gen_rtx_REG (DImode, regno);
      do_spill (gen_gr_spill, reg, cfa_off += 8, NULL_RTX);
    }

  /* Locate the bottom of the register save area.  */
  cfa_off = (current_frame_info.spill_cfa_off
	     + current_frame_info.spill_size
	     + current_frame_info.extra_spill_size);

  /* Save the predicate register block either in a register or in memory.  */
  if (TEST_HARD_REG_BIT (current_frame_info.mask, PR_REG (0)))
    {
      reg = gen_rtx_REG (DImode, PR_REG (0));
      if (current_frame_info.reg_save_pr != 0)
	{
	  alt_reg = gen_rtx_REG (DImode, current_frame_info.reg_save_pr);
	  insn = emit_move_insn (alt_reg, reg);

	  /* ??? Denote pr spill/fill by a DImode move that modifies all
	     64 hard registers.  */
	  RTX_FRAME_RELATED_P (insn) = 1;
	  REG_NOTES (insn)
	    = gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
			gen_rtx_SET (VOIDmode, alt_reg, reg),
			REG_NOTES (insn));

	  /* Even if we're not going to generate an epilogue, we still
	     need to save the register so that EH works.  */
	  if (! epilogue_p)
	    emit_insn (gen_rtx_USE (VOIDmode, alt_reg));
	}
      else
	{
	  alt_regno = next_scratch_gr_reg ();
	  alt_reg = gen_rtx_REG (DImode, alt_regno);
	  insn = emit_move_insn (alt_reg, reg);
	  do_spill (gen_movdi_x, alt_reg, cfa_off, reg);
	  cfa_off -= 8;
	}
    }

  /* Handle AR regs in numerical order.  All of them get special handling.  */
  if (TEST_HARD_REG_BIT (current_frame_info.mask, AR_UNAT_REGNUM)
      && current_frame_info.reg_save_ar_unat == 0)
    {
      reg = gen_rtx_REG (DImode, AR_UNAT_REGNUM);
      do_spill (gen_movdi_x, ar_unat_save_reg, cfa_off, reg);
      cfa_off -= 8;
    }

  /* The alloc insn already copied ar.pfs into a general register.  The
     only thing we have to do now is copy that register to a stack slot
     if we'd not allocated a local register for the job.  */
  if (current_frame_info.reg_save_ar_pfs == 0
      && ! current_function_is_leaf)
    {
      reg = gen_rtx_REG (DImode, AR_PFS_REGNUM);
      do_spill (gen_movdi_x, ar_pfs_save_reg, cfa_off, reg);
      cfa_off -= 8;
    }

  if (TEST_HARD_REG_BIT (current_frame_info.mask, AR_LC_REGNUM))
    {
      reg = gen_rtx_REG (DImode, AR_LC_REGNUM);
      if (current_frame_info.reg_save_ar_lc != 0)
	{
	  alt_reg = gen_rtx_REG (DImode, current_frame_info.reg_save_ar_lc);
	  insn = emit_move_insn (alt_reg, reg);
	  RTX_FRAME_RELATED_P (insn) = 1;

	  /* Even if we're not going to generate an epilogue, we still
	     need to save the register so that EH works.  */
	  if (! epilogue_p)
	    emit_insn (gen_rtx_USE (VOIDmode, alt_reg));
	}
      else
	{
	  alt_regno = next_scratch_gr_reg ();
	  alt_reg = gen_rtx_REG (DImode, alt_regno);
	  emit_move_insn (alt_reg, reg);
	  do_spill (gen_movdi_x, alt_reg, cfa_off, reg);
	  cfa_off -= 8;
	}
    }

  /* We should now be at the base of the gr/br/fr spill area.  */
  if (cfa_off != (current_frame_info.spill_cfa_off
		  + current_frame_info.spill_size))
    abort ();

  /* Spill all general registers.  */
  for (regno = GR_REG (1); regno <= GR_REG (31); ++regno)
    if (TEST_HARD_REG_BIT (current_frame_info.mask, regno))
      {
	reg = gen_rtx_REG (DImode, regno);
	do_spill (gen_gr_spill, reg, cfa_off, reg);
	cfa_off -= 8;
      }

  /* Handle BR0 specially -- it may be getting stored permanently in
     some GR register.  */
  if (TEST_HARD_REG_BIT (current_frame_info.mask, BR_REG (0)))
    {
      reg = gen_rtx_REG (DImode, BR_REG (0));
      if (current_frame_info.reg_save_b0 != 0)
	{
	  alt_reg = gen_rtx_REG (DImode, current_frame_info.reg_save_b0);
	  insn = emit_move_insn (alt_reg, reg);
	  RTX_FRAME_RELATED_P (insn) = 1;

	  /* Even if we're not going to generate an epilogue, we still
	     need to save the register so that EH works.  */
	  if (! epilogue_p)
	    emit_insn (gen_rtx_USE (VOIDmode, alt_reg));
	}
      else
	{
	  alt_regno = next_scratch_gr_reg ();
	  alt_reg = gen_rtx_REG (DImode, alt_regno);
	  emit_move_insn (alt_reg, reg);
	  do_spill (gen_movdi_x, alt_reg, cfa_off, reg);
	  cfa_off -= 8;
	}
    }

  /* Spill the rest of the BR registers.  */
  for (regno = BR_REG (1); regno <= BR_REG (7); ++regno)
    if (TEST_HARD_REG_BIT (current_frame_info.mask, regno))
      {
	alt_regno = next_scratch_gr_reg ();
	alt_reg = gen_rtx_REG (DImode, alt_regno);
	reg = gen_rtx_REG (DImode, regno);
	emit_move_insn (alt_reg, reg);
	do_spill (gen_movdi_x, alt_reg, cfa_off, reg);
	cfa_off -= 8;
      }

  /* Align the frame and spill all FR registers.  */
  for (regno = FR_REG (2); regno <= FR_REG (127); ++regno)
    if (TEST_HARD_REG_BIT (current_frame_info.mask, regno))
      {
        if (cfa_off & 15)
	  abort ();
	reg = gen_rtx_REG (TFmode, regno);
	do_spill (gen_fr_spill_x, reg, cfa_off, reg);
	cfa_off -= 16;
      }

  if (cfa_off != current_frame_info.spill_cfa_off)
    abort ();

  finish_spill_pointers ();
}

/* Called after register allocation to add any instructions needed for the
   epilogue.  Using a epilogue insn is favored compared to putting all of the
   instructions in the FUNCTION_PROLOGUE macro, since it allows the scheduler
   to intermix instructions with the saves of the caller saved registers.  In
   some cases, it might be necessary to emit a barrier instruction as the last
   insn to prevent such scheduling.  */

void
ia64_expand_epilogue (sibcall_p)
     int sibcall_p;
{
  rtx insn, reg, alt_reg, ar_unat_save_reg;
  int regno, alt_regno, cfa_off;

  ia64_compute_frame_size (get_frame_size ());

  /* If there is a frame pointer, then we use it instead of the stack
     pointer, so that the stack pointer does not need to be valid when
     the epilogue starts.  See EXIT_IGNORE_STACK.  */
  if (frame_pointer_needed)
    setup_spill_pointers (current_frame_info.n_spilled,
			  hard_frame_pointer_rtx, 0);
  else
    setup_spill_pointers (current_frame_info.n_spilled, stack_pointer_rtx, 
			  current_frame_info.total_size);

  if (current_frame_info.total_size != 0)
    {
      /* ??? At this point we must generate a magic insn that appears to
         modify the spill iterators and the frame pointer.  This would
	 allow the most scheduling freedom.  For now, just hard stop.  */
      emit_insn (gen_blockage ());
    }

  /* Locate the bottom of the register save area.  */
  cfa_off = (current_frame_info.spill_cfa_off
	     + current_frame_info.spill_size
	     + current_frame_info.extra_spill_size);

  /* Restore the predicate registers.  */
  if (TEST_HARD_REG_BIT (current_frame_info.mask, PR_REG (0)))
    {
      if (current_frame_info.reg_save_pr != 0)
	alt_reg = gen_rtx_REG (DImode, current_frame_info.reg_save_pr);
      else
	{
	  alt_regno = next_scratch_gr_reg ();
	  alt_reg = gen_rtx_REG (DImode, alt_regno);
	  do_restore (gen_movdi_x, alt_reg, cfa_off);
	  cfa_off -= 8;
	}
      reg = gen_rtx_REG (DImode, PR_REG (0));
      emit_move_insn (reg, alt_reg);
    }

  /* Restore the application registers.  */

  /* Load the saved unat from the stack, but do not restore it until
     after the GRs have been restored.  */
  if (TEST_HARD_REG_BIT (current_frame_info.mask, AR_UNAT_REGNUM))
    {
      if (current_frame_info.reg_save_ar_unat != 0)
        ar_unat_save_reg
	  = gen_rtx_REG (DImode, current_frame_info.reg_save_ar_unat);
      else
	{
	  alt_regno = next_scratch_gr_reg ();
	  ar_unat_save_reg = gen_rtx_REG (DImode, alt_regno);
	  current_frame_info.gr_used_mask |= 1 << alt_regno;
	  do_restore (gen_movdi_x, ar_unat_save_reg, cfa_off);
	  cfa_off -= 8;
	}
    }
  else
    ar_unat_save_reg = NULL_RTX;
      
  if (current_frame_info.reg_save_ar_pfs != 0)
    {
      alt_reg = gen_rtx_REG (DImode, current_frame_info.reg_save_ar_pfs);
      reg = gen_rtx_REG (DImode, AR_PFS_REGNUM);
      emit_move_insn (reg, alt_reg);
    }
  else if (! current_function_is_leaf)
    {
      alt_regno = next_scratch_gr_reg ();
      alt_reg = gen_rtx_REG (DImode, alt_regno);
      do_restore (gen_movdi_x, alt_reg, cfa_off);
      cfa_off -= 8;
      reg = gen_rtx_REG (DImode, AR_PFS_REGNUM);
      emit_move_insn (reg, alt_reg);
    }

  if (TEST_HARD_REG_BIT (current_frame_info.mask, AR_LC_REGNUM))
    {
      if (current_frame_info.reg_save_ar_lc != 0)
	alt_reg = gen_rtx_REG (DImode, current_frame_info.reg_save_ar_lc);
      else
	{
	  alt_regno = next_scratch_gr_reg ();
	  alt_reg = gen_rtx_REG (DImode, alt_regno);
	  do_restore (gen_movdi_x, alt_reg, cfa_off);
	  cfa_off -= 8;
	}
      reg = gen_rtx_REG (DImode, AR_LC_REGNUM);
      emit_move_insn (reg, alt_reg);
    }

  /* We should now be at the base of the gr/br/fr spill area.  */
  if (cfa_off != (current_frame_info.spill_cfa_off
		  + current_frame_info.spill_size))
    abort ();

  /* Restore all general registers.  */
  for (regno = GR_REG (1); regno <= GR_REG (31); ++regno)
    if (TEST_HARD_REG_BIT (current_frame_info.mask, regno))
      {
	reg = gen_rtx_REG (DImode, regno);
	do_restore (gen_gr_restore, reg, cfa_off);
	cfa_off -= 8;
      }
  
  /* Restore the branch registers.  Handle B0 specially, as it may
     have gotten stored in some GR register.  */
  if (TEST_HARD_REG_BIT (current_frame_info.mask, BR_REG (0)))
    {
      if (current_frame_info.reg_save_b0 != 0)
	alt_reg = gen_rtx_REG (DImode, current_frame_info.reg_save_b0);
      else
	{
	  alt_regno = next_scratch_gr_reg ();
	  alt_reg = gen_rtx_REG (DImode, alt_regno);
	  do_restore (gen_movdi_x, alt_reg, cfa_off);
	  cfa_off -= 8;
	}
      reg = gen_rtx_REG (DImode, BR_REG (0));
      emit_move_insn (reg, alt_reg);
    }
    
  for (regno = BR_REG (1); regno <= BR_REG (7); ++regno)
    if (TEST_HARD_REG_BIT (current_frame_info.mask, regno))
      {
	alt_regno = next_scratch_gr_reg ();
	alt_reg = gen_rtx_REG (DImode, alt_regno);
	do_restore (gen_movdi_x, alt_reg, cfa_off);
	cfa_off -= 8;
	reg = gen_rtx_REG (DImode, regno);
	emit_move_insn (reg, alt_reg);
      }

  /* Restore floating point registers.  */
  for (regno = FR_REG (2); regno <= FR_REG (127); ++regno)
    if (TEST_HARD_REG_BIT (current_frame_info.mask, regno))
      {
        if (cfa_off & 15)
	  abort ();
	reg = gen_rtx_REG (TFmode, regno);
	do_restore (gen_fr_restore_x, reg, cfa_off);
	cfa_off -= 16;
      }

  /* Restore ar.unat for real.  */
  if (TEST_HARD_REG_BIT (current_frame_info.mask, AR_UNAT_REGNUM))
    {
      reg = gen_rtx_REG (DImode, AR_UNAT_REGNUM);
      emit_move_insn (reg, ar_unat_save_reg);
    }

  if (cfa_off != current_frame_info.spill_cfa_off)
    abort ();

  finish_spill_pointers ();

  if (current_frame_info.total_size || cfun->machine->ia64_eh_epilogue_sp)
    {
      /* ??? At this point we must generate a magic insn that appears to
         modify the spill iterators, the stack pointer, and the frame
	 pointer.  This would allow the most scheduling freedom.  For now,
	 just hard stop.  */
      emit_insn (gen_blockage ());
    }

  if (cfun->machine->ia64_eh_epilogue_sp)
    emit_move_insn (stack_pointer_rtx, cfun->machine->ia64_eh_epilogue_sp);
  else if (frame_pointer_needed)
    {
      insn = emit_move_insn (stack_pointer_rtx, hard_frame_pointer_rtx);
      RTX_FRAME_RELATED_P (insn) = 1;
    }
  else if (current_frame_info.total_size)
    {
      rtx offset, frame_size_rtx;

      frame_size_rtx = GEN_INT (current_frame_info.total_size);
      if (CONST_OK_FOR_I (current_frame_info.total_size))
	offset = frame_size_rtx;
      else
	{
	  regno = next_scratch_gr_reg ();
	  offset = gen_rtx_REG (DImode, regno);
	  emit_move_insn (offset, frame_size_rtx);
	}

      insn = emit_insn (gen_adddi3 (stack_pointer_rtx, stack_pointer_rtx,
				    offset));

      RTX_FRAME_RELATED_P (insn) = 1;
      if (GET_CODE (offset) != CONST_INT)
	{
	  REG_NOTES (insn)
	    = gen_rtx_EXPR_LIST (REG_FRAME_RELATED_EXPR,
			gen_rtx_SET (VOIDmode,
				     stack_pointer_rtx,
				     gen_rtx_PLUS (DImode,
						   stack_pointer_rtx,
						   frame_size_rtx)),
			REG_NOTES (insn));
	}
    }

  if (cfun->machine->ia64_eh_epilogue_bsp)
    emit_insn (gen_set_bsp (cfun->machine->ia64_eh_epilogue_bsp));
 
  if (! sibcall_p)
    emit_jump_insn (gen_return_internal (gen_rtx_REG (DImode, BR_REG (0))));
}

/* Return 1 if br.ret can do all the work required to return from a
   function.  */

int
ia64_direct_return ()
{
  if (reload_completed && ! frame_pointer_needed)
    {
      ia64_compute_frame_size (get_frame_size ());

      return (current_frame_info.total_size == 0
	      && current_frame_info.n_spilled == 0
	      && current_frame_info.reg_save_b0 == 0
	      && current_frame_info.reg_save_pr == 0
	      && current_frame_info.reg_save_ar_pfs == 0
	      && current_frame_info.reg_save_ar_unat == 0
	      && current_frame_info.reg_save_ar_lc == 0);
    }
  return 0;
}

int
ia64_hard_regno_rename_ok (from, to)
     int from;
     int to;
{
  /* Don't clobber any of the registers we reserved for the prologue.  */
  if (to == current_frame_info.reg_fp
      || to == current_frame_info.reg_save_b0
      || to == current_frame_info.reg_save_pr
      || to == current_frame_info.reg_save_ar_pfs
      || to == current_frame_info.reg_save_ar_unat
      || to == current_frame_info.reg_save_ar_lc)
    return 0;

  if (from == current_frame_info.reg_fp
      || from == current_frame_info.reg_save_b0
      || from == current_frame_info.reg_save_pr
      || from == current_frame_info.reg_save_ar_pfs
      || from == current_frame_info.reg_save_ar_unat
      || from == current_frame_info.reg_save_ar_lc)
    return 0;

  /* Don't use output registers outside the register frame.  */
  if (OUT_REGNO_P (to) && to >= OUT_REG (current_frame_info.n_output_regs))
    return 0;

  /* Retain even/oddness on predicate register pairs.  */
  if (PR_REGNO_P (from) && PR_REGNO_P (to))
    return (from & 1) == (to & 1);

  /* Reg 4 contains the saved gp; we can't reliably rename this.  */
  if (from == GR_REG (4) && current_function_calls_setjmp)
    return 0;

  return 1;
}

/* Emit the function prologue.  */

void
ia64_function_prologue (file, size)
     FILE *file;
     int size ATTRIBUTE_UNUSED;
{
  int mask, grsave, grsave_prev;

  if (current_frame_info.need_regstk)
    fprintf (file, "\t.regstk %d, %d, %d, %d\n",
	     current_frame_info.n_input_regs,
	     current_frame_info.n_local_regs,
	     current_frame_info.n_output_regs,
	     current_frame_info.n_rotate_regs);

  if (!flag_unwind_tables && (!flag_exceptions || USING_SJLJ_EXCEPTIONS))
    return;

  /* Emit the .prologue directive.  */

  mask = 0;
  grsave = grsave_prev = 0;
  if (current_frame_info.reg_save_b0 != 0)
    {
      mask |= 8;
      grsave = grsave_prev = current_frame_info.reg_save_b0;
    }
  if (current_frame_info.reg_save_ar_pfs != 0
      && (grsave_prev == 0
	  || current_frame_info.reg_save_ar_pfs == grsave_prev + 1))
    {
      mask |= 4;
      if (grsave_prev == 0)
	grsave = current_frame_info.reg_save_ar_pfs;
      grsave_prev = current_frame_info.reg_save_ar_pfs;
    }
  if (current_frame_info.reg_fp != 0
      && (grsave_prev == 0
	  || current_frame_info.reg_fp == grsave_prev + 1))
    {
      mask |= 2;
      if (grsave_prev == 0)
	grsave = HARD_FRAME_POINTER_REGNUM;
      grsave_prev = current_frame_info.reg_fp;
    }
  if (current_frame_info.reg_save_pr != 0
      && (grsave_prev == 0
	  || current_frame_info.reg_save_pr == grsave_prev + 1))
    {
      mask |= 1;
      if (grsave_prev == 0)
	grsave = current_frame_info.reg_save_pr;
    }

  if (mask)
    fprintf (file, "\t.prologue %d, %d\n", mask,
	     ia64_dbx_register_number (grsave));
  else
    fputs ("\t.prologue\n", file);

  /* Emit a .spill directive, if necessary, to relocate the base of
     the register spill area.  */
  if (current_frame_info.spill_cfa_off != -16)
    fprintf (file, "\t.spill %ld\n",
	     (long) (current_frame_info.spill_cfa_off
		     + current_frame_info.spill_size));
}

/* Emit the .body directive at the scheduled end of the prologue.  */

void
ia64_output_end_prologue (file)
     FILE *file;
{
  if (!flag_unwind_tables && (!flag_exceptions || USING_SJLJ_EXCEPTIONS))
    return;

  fputs ("\t.body\n", file);
}

/* Emit the function epilogue.  */

void
ia64_function_epilogue (file, size)
     FILE *file ATTRIBUTE_UNUSED;
     int size ATTRIBUTE_UNUSED;
{
  int i;

  /* Reset from the function's potential modifications.  */
  XINT (return_address_pointer_rtx, 0) = RETURN_ADDRESS_POINTER_REGNUM;

  if (current_frame_info.reg_fp)
    {
      const char *tmp = reg_names[HARD_FRAME_POINTER_REGNUM];
      reg_names[HARD_FRAME_POINTER_REGNUM]
	= reg_names[current_frame_info.reg_fp];
      reg_names[current_frame_info.reg_fp] = tmp;
    }
  if (! TARGET_REG_NAMES)
    {
      for (i = 0; i < current_frame_info.n_input_regs; i++)
	reg_names[IN_REG (i)] = ia64_input_reg_names[i];
      for (i = 0; i < current_frame_info.n_local_regs; i++)
	reg_names[LOC_REG (i)] = ia64_local_reg_names[i];
      for (i = 0; i < current_frame_info.n_output_regs; i++)
	reg_names[OUT_REG (i)] = ia64_output_reg_names[i];
    }

  current_frame_info.initialized = 0;
}

int
ia64_dbx_register_number (regno)
     int regno;
{
  /* In ia64_expand_prologue we quite literally renamed the frame pointer
     from its home at loc79 to something inside the register frame.  We
     must perform the same renumbering here for the debug info.  */
  if (current_frame_info.reg_fp)
    {
      if (regno == HARD_FRAME_POINTER_REGNUM)
	regno = current_frame_info.reg_fp;
      else if (regno == current_frame_info.reg_fp)
	regno = HARD_FRAME_POINTER_REGNUM;
    }

  if (IN_REGNO_P (regno))
    return 32 + regno - IN_REG (0);
  else if (LOC_REGNO_P (regno))
    return 32 + current_frame_info.n_input_regs + regno - LOC_REG (0);
  else if (OUT_REGNO_P (regno))
    return (32 + current_frame_info.n_input_regs
	    + current_frame_info.n_local_regs + regno - OUT_REG (0));
  else
    return regno;
}

void
ia64_initialize_trampoline (addr, fnaddr, static_chain)
     rtx addr, fnaddr, static_chain;
{
  rtx addr_reg, eight = GEN_INT (8);

  /* Load up our iterator.  */
  addr_reg = gen_reg_rtx (Pmode);
  emit_move_insn (addr_reg, addr);

  /* The first two words are the fake descriptor:
     __ia64_trampoline, ADDR+16.  */
  emit_move_insn (gen_rtx_MEM (Pmode, addr_reg),
		  gen_rtx_SYMBOL_REF (Pmode, "__ia64_trampoline"));
  emit_insn (gen_adddi3 (addr_reg, addr_reg, eight));

  emit_move_insn (gen_rtx_MEM (Pmode, addr_reg),
		  copy_to_reg (plus_constant (addr, 16)));
  emit_insn (gen_adddi3 (addr_reg, addr_reg, eight));

  /* The third word is the target descriptor.  */
  emit_move_insn (gen_rtx_MEM (Pmode, addr_reg), fnaddr);
  emit_insn (gen_adddi3 (addr_reg, addr_reg, eight));

  /* The fourth word is the static chain.  */
  emit_move_insn (gen_rtx_MEM (Pmode, addr_reg), static_chain);
}

/* Do any needed setup for a variadic function.  CUM has not been updated
   for the last named argument which has type TYPE and mode MODE.

   We generate the actual spill instructions during prologue generation.  */

void
ia64_setup_incoming_varargs (cum, int_mode, type, pretend_size, second_time)
     CUMULATIVE_ARGS cum;
     int             int_mode;
     tree            type;
     int *           pretend_size;
     int	     second_time ATTRIBUTE_UNUSED;
{
  /* If this is a stdarg function, then skip the current argument.  */
  if (! current_function_varargs)
    ia64_function_arg_advance (&cum, int_mode, type, 1);

  if (cum.words < MAX_ARGUMENT_SLOTS)
    {
      int n = MAX_ARGUMENT_SLOTS - cum.words;
      *pretend_size = n * UNITS_PER_WORD;
      cfun->machine->n_varargs = n;
    }
}

/* Check whether TYPE is a homogeneous floating point aggregate.  If
   it is, return the mode of the floating point type that appears
   in all leafs.  If it is not, return VOIDmode.

   An aggregate is a homogeneous floating point aggregate is if all
   fields/elements in it have the same floating point type (e.g,
   SFmode).  128-bit quad-precision floats are excluded.  */

static enum machine_mode
hfa_element_mode (type, nested)
     tree type;
     int nested;
{
  enum machine_mode element_mode = VOIDmode;
  enum machine_mode mode;
  enum tree_code code = TREE_CODE (type);
  int know_element_mode = 0;
  tree t;

  switch (code)
    {
    case VOID_TYPE:	case INTEGER_TYPE:	case ENUMERAL_TYPE:
    case BOOLEAN_TYPE:	case CHAR_TYPE:		case POINTER_TYPE:
    case OFFSET_TYPE:	case REFERENCE_TYPE:	case METHOD_TYPE:
    case FILE_TYPE:	case SET_TYPE:		case LANG_TYPE:
    case FUNCTION_TYPE:
      return VOIDmode;

      /* Fortran complex types are supposed to be HFAs, so we need to handle
	 gcc's COMPLEX_TYPEs as HFAs.  We need to exclude the integral complex
	 types though.  */
    case COMPLEX_TYPE:
      if (GET_MODE_CLASS (TYPE_MODE (type)) == MODE_COMPLEX_FLOAT)
	return mode_for_size (GET_MODE_UNIT_SIZE (TYPE_MODE (type))
			      * BITS_PER_UNIT, MODE_FLOAT, 0);
      else
	return VOIDmode;

    case REAL_TYPE:
      /* We want to return VOIDmode for raw REAL_TYPEs, but the actual
	 mode if this is contained within an aggregate.  */
      if (nested)
	return TYPE_MODE (type);
      else
	return VOIDmode;

    case ARRAY_TYPE:
      return TYPE_MODE (TREE_TYPE (type));

    case RECORD_TYPE:
    case UNION_TYPE:
    case QUAL_UNION_TYPE:
      for (t = TYPE_FIELDS (type); t; t = TREE_CHAIN (t))
	{
	  if (TREE_CODE (t) != FIELD_DECL)
	    continue;

	  mode = hfa_element_mode (TREE_TYPE (t), 1);
	  if (know_element_mode)
	    {
	      if (mode != element_mode)
		return VOIDmode;
	    }
	  else if (GET_MODE_CLASS (mode) != MODE_FLOAT)
	    return VOIDmode;
	  else
	    {
	      know_element_mode = 1;
	      element_mode = mode;
	    }
	}
      return element_mode;

    default:
      /* If we reach here, we probably have some front-end specific type
	 that the backend doesn't know about.  This can happen via the
	 aggregate_value_p call in init_function_start.  All we can do is
	 ignore unknown tree types.  */
      return VOIDmode;
    }

  return VOIDmode;
}

/* Return rtx for register where argument is passed, or zero if it is passed
   on the stack.  */

/* ??? 128-bit quad-precision floats are always passed in general
   registers.  */

rtx
ia64_function_arg (cum, mode, type, named, incoming)
     CUMULATIVE_ARGS *cum;
     enum machine_mode mode;
     tree type;
     int named;
     int incoming;
{
  int basereg = (incoming ? GR_ARG_FIRST : AR_ARG_FIRST);
  int words = (((mode == BLKmode ? int_size_in_bytes (type)
		 : GET_MODE_SIZE (mode)) + UNITS_PER_WORD - 1)
	       / UNITS_PER_WORD);
  int offset = 0;
  enum machine_mode hfa_mode = VOIDmode;

  /* Integer and float arguments larger than 8 bytes start at the next even
     boundary.  Aggregates larger than 8 bytes start at the next even boundary
     if the aggregate has 16 byte alignment.  Net effect is that types with
     alignment greater than 8 start at the next even boundary.  */
  /* ??? The ABI does not specify how to handle aggregates with alignment from
     9 to 15 bytes, or greater than 16.   We handle them all as if they had
     16 byte alignment.  Such aggregates can occur only if gcc extensions are
     used.  */
  if ((type ? (TYPE_ALIGN (type) > 8 * BITS_PER_UNIT)
       : (words > 1))
      && (cum->words & 1))
    offset = 1;

  /* If all argument slots are used, then it must go on the stack.  */
  if (cum->words + offset >= MAX_ARGUMENT_SLOTS)
    return 0;

  /* Check for and handle homogeneous FP aggregates.  */
  if (type)
    hfa_mode = hfa_element_mode (type, 0);

  /* Unnamed prototyped hfas are passed as usual.  Named prototyped hfas
     and unprototyped hfas are passed specially.  */
  if (hfa_mode != VOIDmode && (! cum->prototype || named))
    {
      rtx loc[16];
      int i = 0;
      int fp_regs = cum->fp_regs;
      int int_regs = cum->words + offset;
      int hfa_size = GET_MODE_SIZE (hfa_mode);
      int byte_size;
      int args_byte_size;

      /* If prototyped, pass it in FR regs then GR regs.
	 If not prototyped, pass it in both FR and GR regs.

	 If this is an SFmode aggregate, then it is possible to run out of
	 FR regs while GR regs are still left.  In that case, we pass the
	 remaining part in the GR regs.  */

      /* Fill the FP regs.  We do this always.  We stop if we reach the end
	 of the argument, the last FP register, or the last argument slot.  */

      byte_size = ((mode == BLKmode)
		   ? int_size_in_bytes (type) : GET_MODE_SIZE (mode));
      args_byte_size = int_regs * UNITS_PER_WORD;
      offset = 0;
      for (; (offset < byte_size && fp_regs < MAX_ARGUMENT_SLOTS
	      && args_byte_size < (MAX_ARGUMENT_SLOTS * UNITS_PER_WORD)); i++)
	{
	  loc[i] = gen_rtx_EXPR_LIST (VOIDmode,
				      gen_rtx_REG (hfa_mode, (FR_ARG_FIRST
							      + fp_regs)),
				      GEN_INT (offset));
	  offset += hfa_size;
	  args_byte_size += hfa_size;
	  fp_regs++;
	}

      /* If no prototype, then the whole thing must go in GR regs.  */
      if (! cum->prototype)
	offset = 0;
      /* If this is an SFmode aggregate, then we might have some left over
	 that needs to go in GR regs.  */
      else if (byte_size != offset)
	int_regs += offset / UNITS_PER_WORD;

      /* Fill in the GR regs.  We must use DImode here, not the hfa mode.  */

      for (; offset < byte_size && int_regs < MAX_ARGUMENT_SLOTS; i++)
	{
	  enum machine_mode gr_mode = DImode;

	  /* If we have an odd 4 byte hunk because we ran out of FR regs,
	     then this goes in a GR reg left adjusted/little endian, right
	     adjusted/big endian.  */
	  /* ??? Currently this is handled wrong, because 4-byte hunks are
	     always right adjusted/little endian.  */
	  if (offset & 0x4)
	    gr_mode = SImode;
	  /* If we have an even 4 byte hunk because the aggregate is a
	     multiple of 4 bytes in size, then this goes in a GR reg right
	     adjusted/little endian.  */
	  else if (byte_size - offset == 4)
	    gr_mode = SImode;

	  loc[i] = gen_rtx_EXPR_LIST (VOIDmode,
				      gen_rtx_REG (gr_mode, (basereg
							     + int_regs)),
				      GEN_INT (offset));
	  offset += GET_MODE_SIZE (gr_mode);
	  int_regs++;
	}

      /* If we ended up using just one location, just return that one loc.  */
      if (i == 1)
	return XEXP (loc[0], 0);
      else
	return gen_rtx_PARALLEL (mode, gen_rtvec_v (i, loc));
    }

  /* Integral and aggregates go in general registers.  If we have run out of
     FR registers, then FP values must also go in general registers.  This can
     happen when we have a SFmode HFA.  */
  else if (! FLOAT_MODE_P (mode) || cum->fp_regs == MAX_ARGUMENT_SLOTS)
    return gen_rtx_REG (mode, basereg + cum->words + offset);

  /* If there is a prototype, then FP values go in a FR register when
     named, and in a GR registeer when unnamed.  */
  else if (cum->prototype)
    {
      if (! named)
	return gen_rtx_REG (mode, basereg + cum->words + offset);
      else
	return gen_rtx_REG (mode, FR_ARG_FIRST + cum->fp_regs);
    }
  /* If there is no prototype, then FP values go in both FR and GR
     registers.  */
  else
    {
      rtx fp_reg = gen_rtx_EXPR_LIST (VOIDmode,
				      gen_rtx_REG (mode, (FR_ARG_FIRST
							  + cum->fp_regs)),
				      const0_rtx);
      rtx gr_reg = gen_rtx_EXPR_LIST (VOIDmode,
				      gen_rtx_REG (mode,
						   (basereg + cum->words
						    + offset)),
				      const0_rtx);

      return gen_rtx_PARALLEL (mode, gen_rtvec (2, fp_reg, gr_reg));
    }
}

/* Return number of words, at the beginning of the argument, that must be
   put in registers.  0 is the argument is entirely in registers or entirely
   in memory.  */

int
ia64_function_arg_partial_nregs (cum, mode, type, named)
     CUMULATIVE_ARGS *cum;
     enum machine_mode mode;
     tree type;
     int named ATTRIBUTE_UNUSED;
{
  int words = (((mode == BLKmode ? int_size_in_bytes (type)
		 : GET_MODE_SIZE (mode)) + UNITS_PER_WORD - 1)
	       / UNITS_PER_WORD);
  int offset = 0;

  /* Arguments with alignment larger than 8 bytes start at the next even
     boundary.  */
  if ((type ? (TYPE_ALIGN (type) > 8 * BITS_PER_UNIT)
       : (words > 1))
      && (cum->words & 1))
    offset = 1;

  /* If all argument slots are used, then it must go on the stack.  */
  if (cum->words + offset >= MAX_ARGUMENT_SLOTS)
    return 0;

  /* It doesn't matter whether the argument goes in FR or GR regs.  If
     it fits within the 8 argument slots, then it goes entirely in
     registers.  If it extends past the last argument slot, then the rest
     goes on the stack.  */

  if (words + cum->words + offset <= MAX_ARGUMENT_SLOTS)
    return 0;

  return MAX_ARGUMENT_SLOTS - cum->words - offset;
}

/* Update CUM to point after this argument.  This is patterned after
   ia64_function_arg.  */

void
ia64_function_arg_advance (cum, mode, type, named)
     CUMULATIVE_ARGS *cum;
     enum machine_mode mode;
     tree type;
     int named;
{
  int words = (((mode == BLKmode ? int_size_in_bytes (type)
		 : GET_MODE_SIZE (mode)) + UNITS_PER_WORD - 1)
	       / UNITS_PER_WORD);
  int offset = 0;
  enum machine_mode hfa_mode = VOIDmode;

  /* If all arg slots are already full, then there is nothing to do.  */
  if (cum->words >= MAX_ARGUMENT_SLOTS)
    return;

  /* Arguments with alignment larger than 8 bytes start at the next even
     boundary.  */
  if ((type ? (TYPE_ALIGN (type) > 8 * BITS_PER_UNIT)
       : (words > 1))
      && (cum->words & 1))
    offset = 1;

  cum->words += words + offset;

  /* Check for and handle homogeneous FP aggregates.  */
  if (type)
    hfa_mode = hfa_element_mode (type, 0);

  /* Unnamed prototyped hfas are passed as usual.  Named prototyped hfas
     and unprototyped hfas are passed specially.  */
  if (hfa_mode != VOIDmode && (! cum->prototype || named))
    {
      int fp_regs = cum->fp_regs;
      /* This is the original value of cum->words + offset.  */
      int int_regs = cum->words - words;
      int hfa_size = GET_MODE_SIZE (hfa_mode);
      int byte_size;
      int args_byte_size;

      /* If prototyped, pass it in FR regs then GR regs.
	 If not prototyped, pass it in both FR and GR regs.

	 If this is an SFmode aggregate, then it is possible to run out of
	 FR regs while GR regs are still left.  In that case, we pass the
	 remaining part in the GR regs.  */

      /* Fill the FP regs.  We do this always.  We stop if we reach the end
	 of the argument, the last FP register, or the last argument slot.  */

      byte_size = ((mode == BLKmode)
		   ? int_size_in_bytes (type) : GET_MODE_SIZE (mode));
      args_byte_size = int_regs * UNITS_PER_WORD;
      offset = 0;
      for (; (offset < byte_size && fp_regs < MAX_ARGUMENT_SLOTS
	      && args_byte_size < (MAX_ARGUMENT_SLOTS * UNITS_PER_WORD));)
	{
	  offset += hfa_size;
	  args_byte_size += hfa_size;
	  fp_regs++;
	}

      cum->fp_regs = fp_regs;
    }

  /* Integral and aggregates go in general registers.  If we have run out of
     FR registers, then FP values must also go in general registers.  This can
     happen when we have a SFmode HFA.  */
  else if (! FLOAT_MODE_P (mode) || cum->fp_regs == MAX_ARGUMENT_SLOTS)
    return;

  /* If there is a prototype, then FP values go in a FR register when
     named, and in a GR registeer when unnamed.  */
  else if (cum->prototype)
    {
      if (! named)
	return;
      else
	/* ??? Complex types should not reach here.  */
	cum->fp_regs += (GET_MODE_CLASS (mode) == MODE_COMPLEX_FLOAT ? 2 : 1);
    }
  /* If there is no prototype, then FP values go in both FR and GR
     registers.  */
  else
    /* ??? Complex types should not reach here.  */
    cum->fp_regs += (GET_MODE_CLASS (mode) == MODE_COMPLEX_FLOAT ? 2 : 1);

  return;
}

/* Implement va_start.  */

void
ia64_va_start (stdarg_p, valist, nextarg)
     int stdarg_p;
     tree valist;
     rtx nextarg;
{
  int arg_words;
  int ofs;

  arg_words = current_function_args_info.words;

  if (stdarg_p)
    ofs = 0;
  else
    ofs = (arg_words >= MAX_ARGUMENT_SLOTS ? -UNITS_PER_WORD : 0);

  nextarg = plus_constant (nextarg, ofs);
  std_expand_builtin_va_start (1, valist, nextarg);
}

/* Implement va_arg.  */

rtx
ia64_va_arg (valist, type)
     tree valist, type;
{
  tree t;

  /* Arguments with alignment larger than 8 bytes start at the next even
     boundary.  */
  if (TYPE_ALIGN (type) > 8 * BITS_PER_UNIT)
    {
      t = build (PLUS_EXPR, TREE_TYPE (valist), valist,
		 build_int_2 (2 * UNITS_PER_WORD - 1, 0));
      t = build (BIT_AND_EXPR, TREE_TYPE (t), t,
		 build_int_2 (-2 * UNITS_PER_WORD, -1));
      t = build (MODIFY_EXPR, TREE_TYPE (valist), valist, t);
      TREE_SIDE_EFFECTS (t) = 1;
      expand_expr (t, const0_rtx, VOIDmode, EXPAND_NORMAL);
    }

  return std_expand_builtin_va_arg (valist, type);
}

/* Return 1 if function return value returned in memory.  Return 0 if it is
   in a register.  */

int
ia64_return_in_memory (valtype)
     tree valtype;
{
  enum machine_mode mode;
  enum machine_mode hfa_mode;
  int byte_size;

  mode = TYPE_MODE (valtype);
  byte_size = ((mode == BLKmode)
	       ? int_size_in_bytes (valtype) : GET_MODE_SIZE (mode));

  /* Hfa's with up to 8 elements are returned in the FP argument registers.  */

  hfa_mode = hfa_element_mode (valtype, 0);
  if (hfa_mode != VOIDmode)
    {
      int hfa_size = GET_MODE_SIZE (hfa_mode);

      if (byte_size / hfa_size > MAX_ARGUMENT_SLOTS)
	return 1;
      else
	return 0;
    }

  else if (byte_size > UNITS_PER_WORD * MAX_INT_RETURN_SLOTS)
    return 1;
  else
    return 0;
}

/* Return rtx for register that holds the function return value.  */

rtx
ia64_function_value (valtype, func)
     tree valtype;
     tree func ATTRIBUTE_UNUSED;
{
  enum machine_mode mode;
  enum machine_mode hfa_mode;

  mode = TYPE_MODE (valtype);
  hfa_mode = hfa_element_mode (valtype, 0);

  if (hfa_mode != VOIDmode)
    {
      rtx loc[8];
      int i;
      int hfa_size;
      int byte_size;
      int offset;

      hfa_size = GET_MODE_SIZE (hfa_mode);
      byte_size = ((mode == BLKmode)
		   ? int_size_in_bytes (valtype) : GET_MODE_SIZE (mode));
      offset = 0;
      for (i = 0; offset < byte_size; i++)
	{
	  loc[i] = gen_rtx_EXPR_LIST (VOIDmode,
				      gen_rtx_REG (hfa_mode, FR_ARG_FIRST + i),
				      GEN_INT (offset));
	  offset += hfa_size;
	}

      if (i == 1)
	return XEXP (loc[0], 0);
      else
	return gen_rtx_PARALLEL (mode, gen_rtvec_v (i, loc));
    }
  else if (FLOAT_TYPE_P (valtype))
    return gen_rtx_REG (mode, FR_ARG_FIRST);
  else
    return gen_rtx_REG (mode, GR_RET_FIRST);
}

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

/* ??? Do we need this?  It gets used only for 'a' operands.  We could perhaps
   also call this from ia64_print_operand for memory addresses.  */

void
ia64_print_operand_address (stream, address)
     FILE * stream ATTRIBUTE_UNUSED;
     rtx    address ATTRIBUTE_UNUSED;
{
}

/* Print an operand to a assembler instruction.
   C	Swap and print a comparison operator.
   D	Print an FP comparison operator.
   E    Print 32 - constant, for SImode shifts as extract.
   e    Print 64 - constant, for DImode rotates.
   F	A floating point constant 0.0 emitted as f0, or 1.0 emitted as f1, or
        a floating point register emitted normally.
   I	Invert a predicate register by adding 1.
   J    Select the proper predicate register for a condition.
   j    Select the inverse predicate register for a condition.
   O	Append .acq for volatile load.
   P	Postincrement of a MEM.
   Q	Append .rel for volatile store.
   S	Shift amount for shladd instruction.
   T	Print an 8-bit sign extended number (K) as a 32-bit unsigned number
	for Intel assembler.
   U	Print an 8-bit sign extended number (K) as a 64-bit unsigned number
	for Intel assembler.
   r	Print register name, or constant 0 as r0.  HP compatibility for
	Linux kernel.  */
void
ia64_print_operand (file, x, code)
     FILE * file;
     rtx    x;
     int    code;
{
  const char *str;

  switch (code)
    {
    case 0:
      /* Handled below.  */
      break;

    case 'C':
      {
	enum rtx_code c = swap_condition (GET_CODE (x));
	fputs (GET_RTX_NAME (c), file);
	return;
      }

    case 'D':
      switch (GET_CODE (x))
	{
	case NE:
	  str = "neq";
	  break;
	case UNORDERED:
	  str = "unord";
	  break;
	case ORDERED:
	  str = "ord";
	  break;
	default:
	  str = GET_RTX_NAME (GET_CODE (x));
	  break;
	}
      fputs (str, file);
      return;

    case 'E':
      fprintf (file, HOST_WIDE_INT_PRINT_DEC, 32 - INTVAL (x));
      return;

    case 'e':
      fprintf (file, HOST_WIDE_INT_PRINT_DEC, 64 - INTVAL (x));
      return;

    case 'F':
      if (x == CONST0_RTX (GET_MODE (x)))
	str = reg_names [FR_REG (0)];
      else if (x == CONST1_RTX (GET_MODE (x)))
	str = reg_names [FR_REG (1)];
      else if (GET_CODE (x) == REG)
	str = reg_names [REGNO (x)];
      else
	abort ();
      fputs (str, file);
      return;

    case 'I':
      fputs (reg_names [REGNO (x) + 1], file);
      return;

    case 'J':
    case 'j':
      {
	unsigned int regno = REGNO (XEXP (x, 0));
	if (GET_CODE (x) == EQ)
	  regno += 1;
	if (code == 'j')
	  regno ^= 1;
        fputs (reg_names [regno], file);
      }
      return;

    case 'O':
      if (MEM_VOLATILE_P (x))
	fputs(".acq", file);
      return;

    case 'P':
      {
	HOST_WIDE_INT value;

	switch (GET_CODE (XEXP (x, 0)))
	  {
	  default:
	    return;

	  case POST_MODIFY:
	    x = XEXP (XEXP (XEXP (x, 0), 1), 1);
	    if (GET_CODE (x) == CONST_INT)
	      value = INTVAL (x);
	    else if (GET_CODE (x) == REG)
	      {
		fprintf (file, ", %s", reg_names[REGNO (x)]);
		return;
	      }
	    else
	      abort ();
	    break;

	  case POST_INC:
	    value = GET_MODE_SIZE (GET_MODE (x));
	    break;

	  case POST_DEC:
	    value = - (HOST_WIDE_INT) GET_MODE_SIZE (GET_MODE (x));
	    break;
	  }

	putc (',', file);
	putc (' ', file);
	fprintf (file, HOST_WIDE_INT_PRINT_DEC, value);
	return;
      }

    case 'Q':
      if (MEM_VOLATILE_P (x))
	fputs(".rel", file);
      return;

    case 'S':
      fprintf (file, "%d", exact_log2 (INTVAL (x)));
      return;

    case 'T':
      if (! TARGET_GNU_AS && GET_CODE (x) == CONST_INT)
	{
	  fprintf (file, "0x%x", (int) INTVAL (x) & 0xffffffff);
	  return;
	}
      break;

    case 'U':
      if (! TARGET_GNU_AS && GET_CODE (x) == CONST_INT)
	{
	  const char *prefix = "0x";
	  if (INTVAL (x) & 0x80000000)
	    {
	      fprintf (file, "0xffffffff");
	      prefix = "";
	    }
	  fprintf (file, "%s%x", prefix, (int) INTVAL (x) & 0xffffffff);
	  return;
	}
      break;

    case 'r':
      /* If this operand is the constant zero, write it as register zero.
	 Any register, zero, or CONST_INT value is OK here.  */
      if (GET_CODE (x) == REG)
	fputs (reg_names[REGNO (x)], file);
      else if (x == CONST0_RTX (GET_MODE (x)))
	fputs ("r0", file);
      else if (GET_CODE (x) == CONST_INT)
	output_addr_const (file, x);
      else
	output_operand_lossage ("invalid %%r value");
      return;

    case '+':
      {
	const char *which;
	
	/* For conditional branches, returns or calls, substitute
	   sptk, dptk, dpnt, or spnt for %s.  */
	x = find_reg_note (current_output_insn, REG_BR_PROB, 0);
	if (x)
	  {
	    int pred_val = INTVAL (XEXP (x, 0));

	    /* Guess top and bottom 10% statically predicted.  */
	    if (pred_val < REG_BR_PROB_BASE / 50)
	      which = ".spnt";
	    else if (pred_val < REG_BR_PROB_BASE / 2)
	      which = ".dpnt";
	    else if (pred_val < REG_BR_PROB_BASE / 100 * 98)
	      which = ".dptk";
	    else
	      which = ".sptk";
	  }
	else if (GET_CODE (current_output_insn) == CALL_INSN)
	  which = ".sptk";
	else
	  which = ".dptk";

	fputs (which, file);
	return;
      }

    case ',':
      x = current_insn_predicate;
      if (x)
	{
	  unsigned int regno = REGNO (XEXP (x, 0));
	  if (GET_CODE (x) == EQ)
	    regno += 1;
          fprintf (file, "(%s) ", reg_names [regno]);
	}
      return;

    default:
      output_operand_lossage ("ia64_print_operand: unknown code");
      return;
    }

  switch (GET_CODE (x))
    {
      /* This happens for the spill/restore instructions.  */
    case POST_INC:
    case POST_DEC:
    case POST_MODIFY:
      x = XEXP (x, 0);
      /* ... fall through ... */

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

    case MEM:
      {
	rtx addr = XEXP (x, 0);
	if (GET_RTX_CLASS (GET_CODE (addr)) == 'a')
	  addr = XEXP (addr, 0);
	fprintf (file, "[%s]", reg_names [REGNO (addr)]);
	break;
      }

    default:
      output_addr_const (file, x);
      break;
    }

  return;
}

/* Calulate the cost of moving data from a register in class FROM to
   one in class TO.  */

int
ia64_register_move_cost (from, to)
     enum reg_class from, to;
{
  int from_hard, to_hard;
  int from_gr, to_gr;
  int from_fr, to_fr;
  int from_pr, to_pr;

  from_hard = (from == BR_REGS || from == AR_M_REGS || from == AR_I_REGS);
  to_hard = (to == BR_REGS || to == AR_M_REGS || to == AR_I_REGS);
  from_gr = (from == GENERAL_REGS);
  to_gr = (to == GENERAL_REGS);
  from_fr = (from == FR_REGS);
  to_fr = (to == FR_REGS);
  from_pr = (from == PR_REGS);
  to_pr = (to == PR_REGS);

  if (from_hard && to_hard)
    return 8;
  else if ((from_hard && !to_gr) || (!from_gr && to_hard))
    return 6;

  /* Moving between PR registers takes two insns.  */
  else if (from_pr && to_pr)
    return 3;
  /* Moving between PR and anything but GR is impossible.  */
  else if ((from_pr && !to_gr) || (!from_gr && to_pr))
    return 6;

  /* ??? Moving from FR<->GR must be more expensive than 2, so that we get
     secondary memory reloads for TFmode moves.  Unfortunately, we don't
     have the mode here, so we can't check that.  */
  /* Moreover, we have to make this at least as high as MEMORY_MOVE_COST
     to avoid spectacularly poor register class preferencing for TFmode.  */
  else if (from_fr != to_fr)
    return 5;

  return 2;
}

/* This function returns the register class required for a secondary
   register when copying between one of the registers in CLASS, and X,
   using MODE.  A return value of NO_REGS means that no secondary register
   is required.  */

enum reg_class
ia64_secondary_reload_class (class, mode, x)
     enum reg_class class;
     enum machine_mode mode ATTRIBUTE_UNUSED;
     rtx x;
{
  int regno = -1;

  if (GET_CODE (x) == REG || GET_CODE (x) == SUBREG)
    regno = true_regnum (x);

  switch (class)
    {
    case BR_REGS:
      /* ??? This is required because of a bad gcse/cse/global interaction.
	 We end up with two pseudos with overlapping lifetimes both of which
	 are equiv to the same constant, and both which need to be in BR_REGS.
	 This results in a BR_REGS to BR_REGS copy which doesn't exist.  To
	 reproduce, return NO_REGS here, and compile divdi3 in libgcc2.c.
	 This seems to be a cse bug.  cse_basic_block_end changes depending
	 on the path length, which means the qty_first_reg check in
	 make_regs_eqv can give different answers at different times.  */
      /* ??? At some point I'll probably need a reload_indi pattern to handle
	 this.  */
      if (BR_REGNO_P (regno))
	return GR_REGS;

      /* This is needed if a pseudo used as a call_operand gets spilled to a
	 stack slot.  */
      if (GET_CODE (x) == MEM)
	return GR_REGS;
      break;

    case FR_REGS:
      /* This can happen when a paradoxical subreg is an operand to the
	 muldi3 pattern.  */
      /* ??? This shouldn't be necessary after instruction scheduling is
	 enabled, because paradoxical subregs are not accepted by
	 register_operand when INSN_SCHEDULING is defined.  Or alternatively,
	 stop the paradoxical subreg stupidity in the *_operand functions
	 in recog.c.  */
      if (GET_CODE (x) == MEM
	  && (GET_MODE (x) == SImode || GET_MODE (x) == HImode
	      || GET_MODE (x) == QImode))
	return GR_REGS;

      /* This can happen because of the ior/and/etc patterns that accept FP
	 registers as operands.  If the third operand is a constant, then it
	 needs to be reloaded into a FP register.  */
      if (GET_CODE (x) == CONST_INT)
	return GR_REGS;

      /* This can happen because of register elimination in a muldi3 insn.
	 E.g. `26107 * (unsigned long)&u'.  */
      if (GET_CODE (x) == PLUS)
	return GR_REGS;
      break;

    case PR_REGS:
      /* ??? This happens if we cse/gcse a BImode value across a call,
	 and the function has a nonlocal goto.  This is because global
	 does not allocate call crossing pseudos to hard registers when
	 current_function_has_nonlocal_goto is true.  This is relatively
	 common for C++ programs that use exceptions.  To reproduce,
	 return NO_REGS and compile libstdc++.  */
      if (GET_CODE (x) == MEM)
	return GR_REGS;

      /* This can happen when we take a BImode subreg of a DImode value,
	 and that DImode value winds up in some non-GR register.  */
      if (regno >= 0 && ! GENERAL_REGNO_P (regno) && ! PR_REGNO_P (regno))
	return GR_REGS;
      break;

    case GR_REGS:
      /* Since we have no offsettable memory addresses, we need a temporary
	 to hold the address of the second word.  */
      if (mode == TImode)
	return GR_REGS;
      break;

    default:
      break;
    }

  return NO_REGS;
}


/* Emit text to declare externally defined variables and functions, because
   the Intel assembler does not support undefined externals.  */

void
ia64_asm_output_external (file, decl, name)
     FILE *file;
     tree decl;
     const char *name;
{
  int save_referenced;

  /* GNU as does not need anything here.  */
  if (TARGET_GNU_AS)
    return;

  /* ??? The Intel assembler creates a reference that needs to be satisfied by
     the linker when we do this, so we need to be careful not to do this for
     builtin functions which have no library equivalent.  Unfortunately, we
     can't tell here whether or not a function will actually be called by
     expand_expr, so we pull in library functions even if we may not need
     them later.  */
  if (! strcmp (name, "__builtin_next_arg")
      || ! strcmp (name, "alloca")
      || ! strcmp (name, "__builtin_constant_p")
      || ! strcmp (name, "__builtin_args_info"))
    return;

  /* assemble_name will set TREE_SYMBOL_REFERENCED, so we must save and
     restore it.  */
  save_referenced = TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl));
  if (TREE_CODE (decl) == FUNCTION_DECL)
    {
      fprintf (file, "%s", TYPE_ASM_OP);
      assemble_name (file, name);
      putc (',', file);
      fprintf (file, TYPE_OPERAND_FMT, "function");
      putc ('\n', file);
    }
  ASM_GLOBALIZE_LABEL (file, name);
  TREE_SYMBOL_REFERENCED (DECL_ASSEMBLER_NAME (decl)) = save_referenced;
}

/* Parse the -mfixed-range= option string.  */

static void
fix_range (const_str)
     const char *const_str;
{
  int i, first, last;
  char *str, *dash, *comma;

  /* str must be of the form REG1'-'REG2{,REG1'-'REG} where REG1 and
     REG2 are either register names or register numbers.  The effect
     of this option is to mark the registers in the range from REG1 to
     REG2 as ``fixed'' so they won't be used by the compiler.  This is
     used, e.g., to ensure that kernel mode code doesn't use f32-f127.  */

  i = strlen (const_str);
  str = (char *) alloca (i + 1);
  memcpy (str, const_str, i + 1);

  while (1)
    {
      dash = strchr (str, '-');
      if (!dash)
	{
	  warning ("value of -mfixed-range must have form REG1-REG2");
	  return;
	}
      *dash = '\0';

      comma = strchr (dash + 1, ',');
      if (comma)
	*comma = '\0';

      first = decode_reg_name (str);
      if (first < 0)
	{
	  warning ("unknown register name: %s", str);
	  return;
	}

      last = decode_reg_name (dash + 1);
      if (last < 0)
	{
	  warning ("unknown register name: %s", dash + 1);
	  return;
	}

      *dash = '-';

      if (first > last)
	{
	  warning ("%s-%s is an empty range", str, dash + 1);
	  return;
	}

      for (i = first; i <= last; ++i)
	fixed_regs[i] = call_used_regs[i] = 1;

      if (!comma)
	break;

      *comma = ',';
      str = comma + 1;
    }
}

/* Called to register all of our global variables with the garbage
   collector.  */

static void
ia64_add_gc_roots ()
{
  ggc_add_rtx_root (&ia64_compare_op0, 1);
  ggc_add_rtx_root (&ia64_compare_op1, 1);
}

static void
ia64_init_machine_status (p)
     struct function *p;
{
  p->machine =
    (struct machine_function *) xcalloc (1, sizeof (struct machine_function));
}

static void
ia64_mark_machine_status (p)
     struct function *p;
{
  struct machine_function *machine = p->machine;

  if (machine)
    {
      ggc_mark_rtx (machine->ia64_eh_epilogue_sp);
      ggc_mark_rtx (machine->ia64_eh_epilogue_bsp);
      ggc_mark_rtx (machine->ia64_gp_save);
    }
}

static void
ia64_free_machine_status (p)
     struct function *p;
{
  free (p->machine);
  p->machine = NULL;
}

/* Handle TARGET_OPTIONS switches.  */

void
ia64_override_options ()
{
  if (TARGET_AUTO_PIC)
    target_flags |= MASK_CONST_GP;

  if (TARGET_INLINE_DIV_LAT && TARGET_INLINE_DIV_THR)
    {
      warning ("cannot optimize division for both latency and throughput");
      target_flags &= ~MASK_INLINE_DIV_THR;
    }

  if (ia64_fixed_range_string)
    fix_range (ia64_fixed_range_string);

  ia64_section_threshold = g_switch_set ? g_switch_value : IA64_DEFAULT_GVALUE;

  init_machine_status = ia64_init_machine_status;
  mark_machine_status = ia64_mark_machine_status;
  free_machine_status = ia64_free_machine_status;

  ia64_add_gc_roots ();
}

static enum attr_itanium_requires_unit0 ia64_safe_itanium_requires_unit0 PARAMS((rtx));
static enum attr_itanium_class ia64_safe_itanium_class PARAMS((rtx));
static enum attr_type ia64_safe_type PARAMS((rtx));

static enum attr_itanium_requires_unit0
ia64_safe_itanium_requires_unit0 (insn)
     rtx insn;
{
  if (recog_memoized (insn) >= 0)
    return get_attr_itanium_requires_unit0 (insn);
  else
    return ITANIUM_REQUIRES_UNIT0_NO;
}

static enum attr_itanium_class
ia64_safe_itanium_class (insn)
     rtx insn;
{
  if (recog_memoized (insn) >= 0)
    return get_attr_itanium_class (insn);
  else
    return ITANIUM_CLASS_UNKNOWN;
}

static enum attr_type
ia64_safe_type (insn)
     rtx insn;
{
  if (recog_memoized (insn) >= 0)
    return get_attr_type (insn);
  else
    return TYPE_UNKNOWN;
}

/* The following collection of routines emit instruction group stop bits as
   necessary to avoid dependencies.  */

/* Need to track some additional registers as far as serialization is
   concerned so we can properly handle br.call and br.ret.  We could
   make these registers visible to gcc, but since these registers are
   never explicitly used in gcc generated code, it seems wasteful to
   do so (plus it would make the call and return patterns needlessly
   complex).  */
#define REG_GP		(GR_REG (1))
#define REG_RP		(BR_REG (0))
#define REG_AR_CFM	(FIRST_PSEUDO_REGISTER + 1)
/* This is used for volatile asms which may require a stop bit immediately
   before and after them.  */
#define REG_VOLATILE	(FIRST_PSEUDO_REGISTER + 2)
#define AR_UNAT_BIT_0	(FIRST_PSEUDO_REGISTER + 3)
#define NUM_REGS	(AR_UNAT_BIT_0 + 64)

/* For each register, we keep track of how it has been written in the
   current instruction group.

   If a register is written unconditionally (no qualifying predicate),
   WRITE_COUNT is set to 2 and FIRST_PRED is ignored.

   If a register is written if its qualifying predicate P is true, we
   set WRITE_COUNT to 1 and FIRST_PRED to P.  Later on, the same register
   may be written again by the complement of P (P^1) and when this happens,
   WRITE_COUNT gets set to 2.

   The result of this is that whenever an insn attempts to write a register
   whose WRITE_COUNT is two, we need to issue a insn group barrier first.

   If a predicate register is written by a floating-point insn, we set
   WRITTEN_BY_FP to true.

   If a predicate register is written by an AND.ORCM we set WRITTEN_BY_AND
   to true; if it was written by an OR.ANDCM we set WRITTEN_BY_OR to true.  */

struct reg_write_state
{
  unsigned int write_count : 2;
  unsigned int first_pred : 16;
  unsigned int written_by_fp : 1;
  unsigned int written_by_and : 1;
  unsigned int written_by_or : 1;
};

/* Cumulative info for the current instruction group.  */
struct reg_write_state rws_sum[NUM_REGS];
/* Info for the current instruction.  This gets copied to rws_sum after a
   stop bit is emitted.  */
struct reg_write_state rws_insn[NUM_REGS];

/* Misc flags needed to compute RAW/WAW dependencies while we are traversing
   RTL for one instruction.  */
struct reg_flags
{
  unsigned int is_write : 1;	/* Is register being written?  */
  unsigned int is_fp : 1;	/* Is register used as part of an fp op?  */
  unsigned int is_branch : 1;	/* Is register used as part of a branch?  */
  unsigned int is_and : 1;	/* Is register used as part of and.orcm?  */
  unsigned int is_or : 1;	/* Is register used as part of or.andcm?  */
  unsigned int is_sibcall : 1;	/* Is this a sibling or normal call?  */
};

static void rws_update PARAMS ((struct reg_write_state *, int,
				struct reg_flags, int));
static int rws_access_regno PARAMS ((int, struct reg_flags, int));
static int rws_access_reg PARAMS ((rtx, struct reg_flags, int));
static void update_set_flags PARAMS ((rtx, struct reg_flags *, int *, rtx *));
static int set_src_needs_barrier PARAMS ((rtx, struct reg_flags, int, rtx));
static int rtx_needs_barrier PARAMS ((rtx, struct reg_flags, int));
static void init_insn_group_barriers PARAMS ((void));
static int group_barrier_needed_p PARAMS ((rtx));
static int safe_group_barrier_needed_p PARAMS ((rtx));

/* Update *RWS for REGNO, which is being written by the current instruction,
   with predicate PRED, and associated register flags in FLAGS.  */

static void
rws_update (rws, regno, flags, pred)
     struct reg_write_state *rws;
     int regno;
     struct reg_flags flags;
     int pred;
{
  rws[regno].write_count += pred ? 1 : 2;
  rws[regno].written_by_fp |= flags.is_fp;
  /* ??? Not tracking and/or across differing predicates.  */
  rws[regno].written_by_and = flags.is_and;
  rws[regno].written_by_or = flags.is_or;
  rws[regno].first_pred = pred;
}

/* Handle an access to register REGNO of type FLAGS using predicate register
   PRED.  Update rws_insn and rws_sum arrays.  Return 1 if this access creates
   a dependency with an earlier instruction in the same group.  */

static int
rws_access_regno (regno, flags, pred)
     int regno;
     struct reg_flags flags;
     int pred;
{
  int need_barrier = 0;

  if (regno >= NUM_REGS)
    abort ();

  if (! PR_REGNO_P (regno))
    flags.is_and = flags.is_or = 0;

  if (flags.is_write)
    {
      int write_count;

      /* One insn writes same reg multiple times?  */
      if (rws_insn[regno].write_count > 0)
	abort ();

      /* Update info for current instruction.  */
      rws_update (rws_insn, regno, flags, pred);
      write_count = rws_sum[regno].write_count;

      switch (write_count)
	{
	case 0:
	  /* The register has not been written yet.  */
	  rws_update (rws_sum, regno, flags, pred);
	  break;

	case 1:
	  /* The register has been written via a predicate.  If this is
	     not a complementary predicate, then we need a barrier.  */
	  /* ??? This assumes that P and P+1 are always complementary
	     predicates for P even.  */
	  if (flags.is_and && rws_sum[regno].written_by_and)
	    ; 
	  else if (flags.is_or && rws_sum[regno].written_by_or)
	    ;
	  else if ((rws_sum[regno].first_pred ^ 1) != pred)
	    need_barrier = 1;
	  rws_update (rws_sum, regno, flags, pred);
	  break;

	case 2:
	  /* The register has been unconditionally written already.  We
	     need a barrier.  */
	  if (flags.is_and && rws_sum[regno].written_by_and)
	    ;
	  else if (flags.is_or && rws_sum[regno].written_by_or)
	    ;
	  else
	    need_barrier = 1;
	  rws_sum[regno].written_by_and = flags.is_and;
	  rws_sum[regno].written_by_or = flags.is_or;
	  break;

	default:
	  abort ();
	}
    }
  else
    {
      if (flags.is_branch)
	{
	  /* Branches have several RAW exceptions that allow to avoid
	     barriers.  */

	  if (REGNO_REG_CLASS (regno) == BR_REGS || regno == AR_PFS_REGNUM)
	    /* RAW dependencies on branch regs are permissible as long
	       as the writer is a non-branch instruction.  Since we
	       never generate code that uses a branch register written
	       by a branch instruction, handling this case is
	       easy.  */
	    return 0;

	  if (REGNO_REG_CLASS (regno) == PR_REGS
	      && ! rws_sum[regno].written_by_fp)
	    /* The predicates of a branch are available within the
	       same insn group as long as the predicate was written by
	       something other than a floating-point instruction.   */
	    return 0;
	}

      if (flags.is_and && rws_sum[regno].written_by_and)
	return 0;
      if (flags.is_or && rws_sum[regno].written_by_or)
	return 0;

      switch (rws_sum[regno].write_count)
	{
	case 0:
	  /* The register has not been written yet.  */
	  break;

	case 1:
	  /* The register has been written via a predicate.  If this is
	     not a complementary predicate, then we need a barrier.  */
	  /* ??? This assumes that P and P+1 are always complementary
	     predicates for P even.  */
	  if ((rws_sum[regno].first_pred ^ 1) != pred)
	    need_barrier = 1;
	  break;

	case 2:
	  /* The register has been unconditionally written already.  We
	     need a barrier.  */
	  need_barrier = 1;
	  break;

	default:
	  abort ();
	}
    }

  return need_barrier;
}

static int
rws_access_reg (reg, flags, pred)
     rtx reg;
     struct reg_flags flags;
     int pred;
{
  int regno = REGNO (reg);
  int n = HARD_REGNO_NREGS (REGNO (reg), GET_MODE (reg));

  if (n == 1)
    return rws_access_regno (regno, flags, pred);
  else
    {
      int need_barrier = 0;
      while (--n >= 0)
	need_barrier |= rws_access_regno (regno + n, flags, pred);
      return need_barrier;
    }
}

/* Examine X, which is a SET rtx, and update the flags, the predicate, and
   the condition, stored in *PFLAGS, *PPRED and *PCOND.  */

static void
update_set_flags (x, pflags, ppred, pcond)
     rtx x;
     struct reg_flags *pflags;
     int *ppred;
     rtx *pcond;
{
  rtx src = SET_SRC (x);

  *pcond = 0;

  switch (GET_CODE (src))
    {
    case CALL:
      return;

    case IF_THEN_ELSE:
      if (SET_DEST (x) == pc_rtx)
	/* X is a conditional branch.  */
	return;	
      else
	{
	  int is_complemented = 0;

	  /* X is a conditional move.  */
	  rtx cond = XEXP (src, 0);
	  if (GET_CODE (cond) == EQ)
	    is_complemented = 1;
	  cond = XEXP (cond, 0);
	  if (GET_CODE (cond) != REG
	      && REGNO_REG_CLASS (REGNO (cond)) != PR_REGS)
	    abort ();
	  *pcond = cond;
	  if (XEXP (src, 1) == SET_DEST (x)
	      || XEXP (src, 2) == SET_DEST (x))
	    {
	      /* X is a conditional move that conditionally writes the
		 destination.  */

	      /* We need another complement in this case.  */
	      if (XEXP (src, 1) == SET_DEST (x))
		is_complemented = ! is_complemented;

	      *ppred = REGNO (cond);
	      if (is_complemented)
		++*ppred;
	    }

	  /* ??? If this is a conditional write to the dest, then this
	     instruction does not actually read one source.  This probably
	     doesn't matter, because that source is also the dest.  */
	  /* ??? Multiple writes to predicate registers are allowed
	     if they are all AND type compares, or if they are all OR
	     type compares.  We do not generate such instructions
	     currently.  */
	}
      /* ... fall through ... */

    default:
      if (GET_RTX_CLASS (GET_CODE (src)) == '<'
	  && GET_MODE_CLASS (GET_MODE (XEXP (src, 0))) == MODE_FLOAT)
	/* Set pflags->is_fp to 1 so that we know we're dealing
	   with a floating point comparison when processing the
	   destination of the SET.  */
	pflags->is_fp = 1;

      /* Discover if this is a parallel comparison.  We only handle
	 and.orcm and or.andcm at present, since we must retain a
	 strict inverse on the predicate pair.  */
      else if (GET_CODE (src) == AND)
	pflags->is_and = 1;
      else if (GET_CODE (src) == IOR)
	pflags->is_or = 1;

      break;
    }
}

/* Subroutine of rtx_needs_barrier; this function determines whether the
   source of a given SET rtx found in X needs a barrier.  FLAGS and PRED
   are as in rtx_needs_barrier.  COND is an rtx that holds the condition
   for this insn.  */
   
static int
set_src_needs_barrier (x, flags, pred, cond)
     rtx x;
     struct reg_flags flags;
     int pred;
     rtx cond;
{
  int need_barrier = 0;
  rtx dst;
  rtx src = SET_SRC (x);

  if (GET_CODE (src) == CALL)
    /* We don't need to worry about the result registers that
       get written by subroutine call.  */
    return rtx_needs_barrier (src, flags, pred);
  else if (SET_DEST (x) == pc_rtx)
    {
      /* X is a conditional branch.  */
      /* ??? This seems redundant, as the caller sets this bit for
	 all JUMP_INSNs.  */
      flags.is_branch = 1;
      return rtx_needs_barrier (src, flags, pred);
    }

  need_barrier = rtx_needs_barrier (src, flags, pred);

  /* This instruction unconditionally uses a predicate register.  */
  if (cond)
    need_barrier |= rws_access_reg (cond, flags, 0);

  dst = SET_DEST (x);
  if (GET_CODE (dst) == ZERO_EXTRACT)
    {
      need_barrier |= rtx_needs_barrier (XEXP (dst, 1), flags, pred);
      need_barrier |= rtx_needs_barrier (XEXP (dst, 2), flags, pred);
      dst = XEXP (dst, 0);
    }
  return need_barrier;
}

/* Handle an access to rtx X of type FLAGS using predicate register PRED.
   Return 1 is this access creates a dependency with an earlier instruction
   in the same group.  */

static int
rtx_needs_barrier (x, flags, pred)
     rtx x;
     struct reg_flags flags;
     int pred;
{
  int i, j;
  int is_complemented = 0;
  int need_barrier = 0;
  const char *format_ptr;
  struct reg_flags new_flags;
  rtx cond = 0;

  if (! x)
    return 0;

  new_flags = flags;

  switch (GET_CODE (x))
    {
    case SET:      
      update_set_flags (x, &new_flags, &pred, &cond);
      need_barrier = set_src_needs_barrier (x, new_flags, pred, cond);
      if (GET_CODE (SET_SRC (x)) != CALL)
	{
	  new_flags.is_write = 1;
	  need_barrier |= rtx_needs_barrier (SET_DEST (x), new_flags, pred);
	}
      break;

    case CALL:
      new_flags.is_write = 0;
      need_barrier |= rws_access_regno (AR_EC_REGNUM, new_flags, pred);

      /* Avoid multiple register writes, in case this is a pattern with
	 multiple CALL rtx.  This avoids an abort in rws_access_reg.  */
      if (! flags.is_sibcall && ! rws_insn[REG_AR_CFM].write_count)
	{
	  new_flags.is_write = 1;
	  need_barrier |= rws_access_regno (REG_RP, new_flags, pred);
	  need_barrier |= rws_access_regno (AR_PFS_REGNUM, new_flags, pred);
	  need_barrier |= rws_access_regno (REG_AR_CFM, new_flags, pred);
	}
      break;

    case COND_EXEC:
      /* X is a predicated instruction.  */

      cond = COND_EXEC_TEST (x);
      if (pred)
	abort ();
      need_barrier = rtx_needs_barrier (cond, flags, 0);

      if (GET_CODE (cond) == EQ)
	is_complemented = 1;
      cond = XEXP (cond, 0);
      if (GET_CODE (cond) != REG
	  && REGNO_REG_CLASS (REGNO (cond)) != PR_REGS)
	abort ();
      pred = REGNO (cond);
      if (is_complemented)
	++pred;

      need_barrier |= rtx_needs_barrier (COND_EXEC_CODE (x), flags, pred);
      return need_barrier;

    case CLOBBER:
    case USE:
      /* Clobber & use are for earlier compiler-phases only.  */
      break;

    case ASM_OPERANDS:
    case ASM_INPUT:
      /* We always emit stop bits for traditional asms.  We emit stop bits
	 for volatile extended asms if TARGET_VOL_ASM_STOP is true.  */
      if (GET_CODE (x) != ASM_OPERANDS
	  || (MEM_VOLATILE_P (x) && TARGET_VOL_ASM_STOP))
	{
	  /* Avoid writing the register multiple times if we have multiple
	     asm outputs.  This avoids an abort in rws_access_reg.  */
	  if (! rws_insn[REG_VOLATILE].write_count)
	    {
	      new_flags.is_write = 1;
	      rws_access_regno (REG_VOLATILE, new_flags, pred);
	    }
	  return 1;
	}

      /* For all ASM_OPERANDS, we must traverse the vector of input operands.
	 We can not just fall through here since then we would be confused
	 by the ASM_INPUT rtx inside ASM_OPERANDS, which do not indicate
	 traditional asms unlike their normal usage.  */

      for (i = ASM_OPERANDS_INPUT_LENGTH (x) - 1; i >= 0; --i)
	if (rtx_needs_barrier (ASM_OPERANDS_INPUT (x, i), flags, pred))
	  need_barrier = 1;
      break;

    case PARALLEL:
      for (i = XVECLEN (x, 0) - 1; i >= 0; --i)
	{
	  rtx pat = XVECEXP (x, 0, i);
	  if (GET_CODE (pat) == SET)
	    {
	      update_set_flags (pat, &new_flags, &pred, &cond);
	      need_barrier |= set_src_needs_barrier (pat, new_flags, pred, cond);
	    }
	  else if (GET_CODE (pat) == USE
		   || GET_CODE (pat) == CALL
		   || GET_CODE (pat) == ASM_OPERANDS)
	    need_barrier |= rtx_needs_barrier (pat, flags, pred);
	  else if (GET_CODE (pat) != CLOBBER && GET_CODE (pat) != RETURN)
	    abort ();
	}
      for (i = XVECLEN (x, 0) - 1; i >= 0; --i)
	{
	  rtx pat = XVECEXP (x, 0, i);
	  if (GET_CODE (pat) == SET)
	    {
	      if (GET_CODE (SET_SRC (pat)) != CALL)
		{
		  new_flags.is_write = 1;
		  need_barrier |= rtx_needs_barrier (SET_DEST (pat), new_flags,
						     pred);
		}
	    }
	  else if (GET_CODE (pat) == CLOBBER)
	    need_barrier |= rtx_needs_barrier (pat, flags, pred);
	}
      break;

    case SUBREG:
      x = SUBREG_REG (x);
      /* FALLTHRU */
    case REG:
      if (REGNO (x) == AR_UNAT_REGNUM)
	{
	  for (i = 0; i < 64; ++i)
	    need_barrier |= rws_access_regno (AR_UNAT_BIT_0 + i, flags, pred);
	}
      else
	need_barrier = rws_access_reg (x, flags, pred);
      break;

    case MEM:
      /* Find the regs used in memory address computation.  */
      new_flags.is_write = 0;
      need_barrier = rtx_needs_barrier (XEXP (x, 0), new_flags, pred);
      break;

    case CONST_INT:   case CONST_DOUBLE:
    case SYMBOL_REF:  case LABEL_REF:     case CONST:
      break;

      /* Operators with side-effects.  */
    case POST_INC:    case POST_DEC:
      if (GET_CODE (XEXP (x, 0)) != REG)
	abort ();

      new_flags.is_write = 0;
      need_barrier  = rws_access_reg (XEXP (x, 0), new_flags, pred);
      new_flags.is_write = 1;
      need_barrier |= rws_access_reg (XEXP (x, 0), new_flags, pred);
      break;

    case POST_MODIFY:
      if (GET_CODE (XEXP (x, 0)) != REG)
	abort ();

      new_flags.is_write = 0;
      need_barrier  = rws_access_reg (XEXP (x, 0), new_flags, pred);
      need_barrier |= rtx_needs_barrier (XEXP (x, 1), new_flags, pred);
      new_flags.is_write = 1;
      need_barrier |= rws_access_reg (XEXP (x, 0), new_flags, pred);
      break;

      /* Handle common unary and binary ops for efficiency.  */
    case COMPARE:  case PLUS:    case MINUS:   case MULT:      case DIV:
    case MOD:      case UDIV:    case UMOD:    case AND:       case IOR:
    case XOR:      case ASHIFT:  case ROTATE:  case ASHIFTRT:  case LSHIFTRT:
    case ROTATERT: case SMIN:    case SMAX:    case UMIN:      case UMAX:
    case NE:       case EQ:      case GE:      case GT:        case LE:
    case LT:       case GEU:     case GTU:     case LEU:       case LTU:
      need_barrier = rtx_needs_barrier (XEXP (x, 0), new_flags, pred);
      need_barrier |= rtx_needs_barrier (XEXP (x, 1), new_flags, pred);
      break;

    case NEG:      case NOT:	        case SIGN_EXTEND:     case ZERO_EXTEND:
    case TRUNCATE: case FLOAT_EXTEND:   case FLOAT_TRUNCATE:  case FLOAT:
    case FIX:      case UNSIGNED_FLOAT: case UNSIGNED_FIX:    case ABS:
    case SQRT:     case FFS:
      need_barrier = rtx_needs_barrier (XEXP (x, 0), flags, pred);
      break;

    case UNSPEC:
      switch (XINT (x, 1))
	{
	case 1: /* st8.spill */
	case 2: /* ld8.fill */
	  {
	    HOST_WIDE_INT offset = INTVAL (XVECEXP (x, 0, 1));
	    HOST_WIDE_INT bit = (offset >> 3) & 63;

	    need_barrier = rtx_needs_barrier (XVECEXP (x, 0, 0), flags, pred);
	    new_flags.is_write = (XINT (x, 1) == 1);
	    need_barrier |= rws_access_regno (AR_UNAT_BIT_0 + bit,
					      new_flags, pred);
	    break;
	  }
	  
	case 3: /* stf.spill */
	case 4: /* ldf.spill */
	case 8: /* popcnt */
	  need_barrier = rtx_needs_barrier (XVECEXP (x, 0, 0), flags, pred);
	  break;

	case 7: /* pred_rel_mutex */
	case 9: /* pic call */
        case 12: /* mf */
        case 19: /* fetchadd_acq */
	case 20: /* mov = ar.bsp */
	case 21: /* flushrs */
	case 22: /* bundle selector */
	case 23: /* cycle display */
          break;

	case 5: /* recip_approx */
	  need_barrier = rtx_needs_barrier (XVECEXP (x, 0, 0), flags, pred);
	  need_barrier |= rtx_needs_barrier (XVECEXP (x, 0, 1), flags, pred);
	  break;

        case 13: /* cmpxchg_acq */
	  need_barrier = rtx_needs_barrier (XVECEXP (x, 0, 1), flags, pred);
	  need_barrier |= rtx_needs_barrier (XVECEXP (x, 0, 2), flags, pred);
	  break;

	default:
	  abort ();
	}
      break;

    case UNSPEC_VOLATILE:
      switch (XINT (x, 1))
	{
	case 0: /* alloc */
	  /* Alloc must always be the first instruction.  Currently, we
	     only emit it at the function start, so we don't need to worry
	     about emitting a stop bit before it.  */
	  need_barrier = rws_access_regno (AR_PFS_REGNUM, flags, pred);

	  new_flags.is_write = 1;
	  need_barrier |= rws_access_regno (REG_AR_CFM, new_flags, pred);
	  return need_barrier;

	case 1: /* blockage */
	case 2: /* insn group barrier */
	  return 0;

	case 5: /* set_bsp  */
	  need_barrier = 1;
          break;

	case 7: /* pred.rel.mutex */
	case 8: /* safe_across_calls all */
	case 9: /* safe_across_calls normal */
	  return 0;

	default:
	  abort ();
	}
      break;

    case RETURN:
      new_flags.is_write = 0;
      need_barrier  = rws_access_regno (REG_RP, flags, pred);
      need_barrier |= rws_access_regno (AR_PFS_REGNUM, flags, pred);

      new_flags.is_write = 1;
      need_barrier |= rws_access_regno (AR_EC_REGNUM, new_flags, pred);
      need_barrier |= rws_access_regno (REG_AR_CFM, new_flags, pred);
      break;

    default:
      format_ptr = GET_RTX_FORMAT (GET_CODE (x));
      for (i = GET_RTX_LENGTH (GET_CODE (x)) - 1; i >= 0; i--)
	switch (format_ptr[i])
	  {
	  case '0':	/* unused field */
	  case 'i':	/* integer */
	  case 'n':	/* note */
	  case 'w':	/* wide integer */
	  case 's':	/* pointer to string */
	  case 'S':	/* optional pointer to string */
	    break;

	  case 'e':
	    if (rtx_needs_barrier (XEXP (x, i), flags, pred))
	      need_barrier = 1;
	    break;

	  case 'E':
	    for (j = XVECLEN (x, i) - 1; j >= 0; --j)
	      if (rtx_needs_barrier (XVECEXP (x, i, j), flags, pred))
		need_barrier = 1;
	    break;

	  default:
	    abort ();
	  }
      break;
    }
  return need_barrier;
}

/* Clear out the state for group_barrier_needed_p at the start of a
   sequence of insns.  */

static void
init_insn_group_barriers ()
{
  memset (rws_sum, 0, sizeof (rws_sum));
}

/* Cumulative info for the current instruction group.  */
struct reg_write_state rws_sum[NUM_REGS];

/* Given the current state, recorded by previous calls to this function,
   determine whether a group barrier (a stop bit) is necessary before INSN.
   Return nonzero if so.  */

static int
group_barrier_needed_p (insn)
     rtx insn;
{
  rtx pat;
  int need_barrier = 0;
  struct reg_flags flags;

  memset (&flags, 0, sizeof (flags));
  switch (GET_CODE (insn))
    {
    case NOTE:
      break;

    case BARRIER:
      /* A barrier doesn't imply an instruction group boundary.  */
      break;

    case CODE_LABEL:
      memset (rws_insn, 0, sizeof (rws_insn));
      return 1;

    case CALL_INSN:
      flags.is_branch = 1;
      flags.is_sibcall = SIBLING_CALL_P (insn);
      memset (rws_insn, 0, sizeof (rws_insn));
      need_barrier = rtx_needs_barrier (PATTERN (insn), flags, 0);
      break;

    case JUMP_INSN:
      flags.is_branch = 1;
      /* FALLTHRU */

    case INSN:
      if (GET_CODE (PATTERN (insn)) == USE
	  || GET_CODE (PATTERN (insn)) == CLOBBER)
	/* Don't care about USE and CLOBBER "insns"---those are used to
	   indicate to the optimizer that it shouldn't get rid of
	   certain operations.  */
	break;

      pat = PATTERN (insn);

      /* Ug.  Hack hacks hacked elsewhere.  */
      switch (recog_memoized (insn))
	{
	  /* We play dependency tricks with the epilogue in order
	     to get proper schedules.  Undo this for dv analysis.  */
	case CODE_FOR_epilogue_deallocate_stack:
	  pat = XVECEXP (pat, 0, 0);
	  break;

	  /* The pattern we use for br.cloop confuses the code above.
	     The second element of the vector is representative.  */
	case CODE_FOR_doloop_end_internal:
	  pat = XVECEXP (pat, 0, 1);
	  break;

	  /* Doesn't generate code.  */
	case CODE_FOR_pred_rel_mutex:
	  return 0;

	default:
	  break;
	}

      memset (rws_insn, 0, sizeof (rws_insn));
      need_barrier = rtx_needs_barrier (pat, flags, 0);

      /* Check to see if the previous instruction was a volatile
	 asm.  */
      if (! need_barrier)
	need_barrier = rws_access_regno (REG_VOLATILE, flags, 0);

      break;

    default:
      abort ();
    }
  return need_barrier;
}

/* Like group_barrier_needed_p, but do not clobber the current state.  */

static int
safe_group_barrier_needed_p (insn)
     rtx insn;
{
  struct reg_write_state rws_saved[NUM_REGS];
  int t;
  memcpy (rws_saved, rws_sum, NUM_REGS * sizeof *rws_saved);
  t = group_barrier_needed_p (insn);
  memcpy (rws_sum, rws_saved, NUM_REGS * sizeof *rws_saved);
  return t;
}

/* INSNS is an chain of instructions.  Scan the chain, and insert stop bits
   as necessary to eliminate dependendencies.  This function assumes that
   a final instruction scheduling pass has been run which has already
   inserted most of the necessary stop bits.  This function only inserts
   new ones at basic block boundaries, since these are invisible to the
   scheduler.  */

static void
emit_insn_group_barriers (dump, insns)
     FILE *dump;
     rtx insns;
{
  rtx insn;
  rtx last_label = 0;
  int insns_since_last_label = 0;

  init_insn_group_barriers ();

  for (insn = insns; insn; insn = NEXT_INSN (insn))
    {
      if (GET_CODE (insn) == CODE_LABEL)
	{
	  if (insns_since_last_label)
	    last_label = insn;
	  insns_since_last_label = 0;
	}
      else if (GET_CODE (insn) == NOTE
	       && NOTE_LINE_NUMBER (insn) == NOTE_INSN_BASIC_BLOCK)
	{
	  if (insns_since_last_label)
	    last_label = insn;
	  insns_since_last_label = 0;
	}
      else if (GET_CODE (insn) == INSN
	       && GET_CODE (PATTERN (insn)) == UNSPEC_VOLATILE
	       && XINT (PATTERN (insn), 1) == 2)
	{
	  init_insn_group_barriers ();
	  last_label = 0;
	}
      else if (INSN_P (insn))
	{
	  insns_since_last_label = 1;

	  if (group_barrier_needed_p (insn))
	    {
	      if (last_label)
		{
		  if (dump)
		    fprintf (dump, "Emitting stop before label %d\n",
			     INSN_UID (last_label));
		  emit_insn_before (gen_insn_group_barrier (GEN_INT (3)), last_label);
		  insn = last_label;

		  init_insn_group_barriers ();
		  last_label = 0;
		}
	    }
	}
    }
}

/* Like emit_insn_group_barriers, but run if no final scheduling pass was run.
   This function has to emit all necessary group barriers.  */

static void
emit_all_insn_group_barriers (dump, insns)
     FILE *dump ATTRIBUTE_UNUSED;
     rtx insns;
{
  rtx insn;

  init_insn_group_barriers ();

  for (insn = insns; insn; insn = NEXT_INSN (insn))
    {
      if (GET_CODE (insn) == INSN
	       && GET_CODE (PATTERN (insn)) == UNSPEC_VOLATILE
	       && XINT (PATTERN (insn), 1) == 2)
	init_insn_group_barriers ();
      else if (INSN_P (insn))
	{
	  if (group_barrier_needed_p (insn))
	    {
	      emit_insn_before (gen_insn_group_barrier (GEN_INT (3)), insn);
	      init_insn_group_barriers ();
	      group_barrier_needed_p (insn);
	    }
	}
    }
}

static int errata_find_address_regs PARAMS ((rtx *, void *));
static void errata_emit_nops PARAMS ((rtx));
static void fixup_errata PARAMS ((void));

/* This structure is used to track some details about the previous insns
   groups so we can determine if it may be necessary to insert NOPs to
   workaround hardware errata.  */
static struct group
{
  HARD_REG_SET p_reg_set;
  HARD_REG_SET gr_reg_conditionally_set;
} last_group[2];

/* Index into the last_group array.  */
static int group_idx;

/* Called through for_each_rtx; determines if a hard register that was
   conditionally set in the previous group is used as an address register.
   It ensures that for_each_rtx returns 1 in that case.  */
static int
errata_find_address_regs (xp, data)
     rtx *xp;
     void *data ATTRIBUTE_UNUSED;
{
  rtx x = *xp;
  if (GET_CODE (x) != MEM)
    return 0;
  x = XEXP (x, 0);
  if (GET_CODE (x) == POST_MODIFY)
    x = XEXP (x, 0);
  if (GET_CODE (x) == REG)
    {
      struct group *prev_group = last_group + (group_idx ^ 1);
      if (TEST_HARD_REG_BIT (prev_group->gr_reg_conditionally_set,
			     REGNO (x)))
	return 1;
      return -1;
    }
  return 0;
}

/* Called for each insn; this function keeps track of the state in
   last_group and emits additional NOPs if necessary to work around
   an Itanium A/B step erratum.  */
static void
errata_emit_nops (insn)
     rtx insn;
{
  struct group *this_group = last_group + group_idx;
  struct group *prev_group = last_group + (group_idx ^ 1);
  rtx pat = PATTERN (insn);
  rtx cond = GET_CODE (pat) == COND_EXEC ? COND_EXEC_TEST (pat) : 0;
  rtx real_pat = cond ? COND_EXEC_CODE (pat) : pat;
  enum attr_type type;
  rtx set = real_pat;

  if (GET_CODE (real_pat) == USE
      || GET_CODE (real_pat) == CLOBBER
      || GET_CODE (real_pat) == ASM_INPUT
      || GET_CODE (real_pat) == ADDR_VEC
      || GET_CODE (real_pat) == ADDR_DIFF_VEC
      || asm_noperands (PATTERN (insn)) >= 0)
    return;

  /* single_set doesn't work for COND_EXEC insns, so we have to duplicate
     parts of it.  */

  if (GET_CODE (set) == PARALLEL)
    {
      int i;
      set = XVECEXP (real_pat, 0, 0);
      for (i = 1; i < XVECLEN (real_pat, 0); i++)
	if (GET_CODE (XVECEXP (real_pat, 0, i)) != USE
	    && GET_CODE (XVECEXP (real_pat, 0, i)) != CLOBBER)
	  {
	    set = 0;
	    break;
	  }
    }

  if (set && GET_CODE (set) != SET)
    set = 0;

  type  = get_attr_type (insn);

  if (type == TYPE_F
      && set && REG_P (SET_DEST (set)) && PR_REGNO_P (REGNO (SET_DEST (set))))
    SET_HARD_REG_BIT (this_group->p_reg_set, REGNO (SET_DEST (set)));

  if ((type == TYPE_M || type == TYPE_A) && cond && set
      && REG_P (SET_DEST (set))
      && GET_CODE (SET_SRC (set)) != PLUS
      && GET_CODE (SET_SRC (set)) != MINUS
      && (GET_CODE (SET_SRC (set)) != ASHIFT
	  || !shladd_operand (XEXP (SET_SRC (set), 1), VOIDmode))
      && (GET_CODE (SET_SRC (set)) != MEM
	  || GET_CODE (XEXP (SET_SRC (set), 0)) != POST_MODIFY)
      && GENERAL_REGNO_P (REGNO (SET_DEST (set))))
    {
      if (GET_RTX_CLASS (GET_CODE (cond)) != '<'
	  || ! REG_P (XEXP (cond, 0)))
	abort ();

      if (TEST_HARD_REG_BIT (prev_group->p_reg_set, REGNO (XEXP (cond, 0))))
	SET_HARD_REG_BIT (this_group->gr_reg_conditionally_set, REGNO (SET_DEST (set)));
    }
  if (for_each_rtx (&real_pat, errata_find_address_regs, NULL))
    {
      emit_insn_before (gen_insn_group_barrier (GEN_INT (3)), insn);
      emit_insn_before (gen_nop (), insn);
      emit_insn_before (gen_insn_group_barrier (GEN_INT (3)), insn);
      group_idx = 0;
      memset (last_group, 0, sizeof last_group);
    }
}

/* Emit extra nops if they are required to work around hardware errata.  */

static void
fixup_errata ()
{
  rtx insn;

  if (! TARGET_B_STEP)
    return;

  group_idx = 0;
  memset (last_group, 0, sizeof last_group);

  for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
    {
      if (!INSN_P (insn))
	continue;

      if (ia64_safe_type (insn) == TYPE_S)
	{
	  group_idx ^= 1;
	  memset (last_group + group_idx, 0, sizeof last_group[group_idx]);
	}
      else
	errata_emit_nops (insn);
    }
}

/* Instruction scheduling support.  */
/* Describe one bundle.  */

struct bundle
{
  /* Zero if there's no possibility of a stop in this bundle other than
     at the end, otherwise the position of the optional stop bit.  */
  int possible_stop;
  /* The types of the three slots.  */
  enum attr_type t[3];
  /* The pseudo op to be emitted into the assembler output.  */
  const char *name;
};

#define NR_BUNDLES 10

/* A list of all available bundles.  */

static const struct bundle bundle[NR_BUNDLES] =
{
  { 2, { TYPE_M, TYPE_I, TYPE_I }, ".mii" },
  { 1, { TYPE_M, TYPE_M, TYPE_I }, ".mmi" },
  { 0, { TYPE_M, TYPE_F, TYPE_I }, ".mfi" },
  { 0, { TYPE_M, TYPE_M, TYPE_F }, ".mmf" },
#if NR_BUNDLES == 10
  { 0, { TYPE_B, TYPE_B, TYPE_B }, ".bbb" },
  { 0, { TYPE_M, TYPE_B, TYPE_B }, ".mbb" },
#endif
  { 0, { TYPE_M, TYPE_I, TYPE_B }, ".mib" },
  { 0, { TYPE_M, TYPE_M, TYPE_B }, ".mmb" },
  { 0, { TYPE_M, TYPE_F, TYPE_B }, ".mfb" },
  /* .mfi needs to occur earlier than .mlx, so that we only generate it if
     it matches an L type insn.  Otherwise we'll try to generate L type
     nops.  */
  { 0, { TYPE_M, TYPE_L, TYPE_X }, ".mlx" }
};

/* Describe a packet of instructions.  Packets consist of two bundles that
   are visible to the hardware in one scheduling window.  */

struct ia64_packet
{
  const struct bundle *t1, *t2;
  /* Precomputed value of the first split issue in this packet if a cycle
     starts at its beginning.  */
  int first_split;
  /* For convenience, the insn types are replicated here so we don't have
     to go through T1 and T2 all the time.  */
  enum attr_type t[6];
};

/* An array containing all possible packets.  */
#define NR_PACKETS (NR_BUNDLES * NR_BUNDLES)
static struct ia64_packet packets[NR_PACKETS];

/* Map attr_type to a string with the name.  */

static const char *type_names[] =
{
  "UNKNOWN", "A", "I", "M", "F", "B", "L", "X", "S"
};

/* Nonzero if we should insert stop bits into the schedule.  */
int ia64_final_schedule = 0;

static int itanium_split_issue PARAMS ((const struct ia64_packet *, int));
static rtx ia64_single_set PARAMS ((rtx));
static int insn_matches_slot PARAMS ((const struct ia64_packet *, enum attr_type, int, rtx));
static void ia64_emit_insn_before PARAMS ((rtx, rtx));
static void maybe_rotate PARAMS ((FILE *));
static void finish_last_head PARAMS ((FILE *, int));
static void rotate_one_bundle PARAMS ((FILE *));
static void rotate_two_bundles PARAMS ((FILE *));
static void cycle_end_fill_slots PARAMS ((FILE *));
static int packet_matches_p PARAMS ((const struct ia64_packet *, int, int *));
static int get_split PARAMS ((const struct ia64_packet *, int));
static int find_best_insn PARAMS ((rtx *, enum attr_type *, int,
				   const struct ia64_packet *, int));
static void find_best_packet PARAMS ((int *, const struct ia64_packet **,
				      rtx *, enum attr_type *, int));
static int itanium_reorder PARAMS ((FILE *, rtx *, rtx *, int));
static void dump_current_packet PARAMS ((FILE *));
static void schedule_stop PARAMS ((FILE *));
static rtx gen_nop_type PARAMS ((enum attr_type));
static void ia64_emit_nops PARAMS ((void));

/* Map a bundle number to its pseudo-op.  */

const char *
get_bundle_name (b)
     int b;
{
  return bundle[b].name;
}

/* Compute the slot which will cause a split issue in packet P if the
   current cycle begins at slot BEGIN.  */

static int
itanium_split_issue (p, begin)
     const struct ia64_packet *p;
     int begin;
{
  int type_count[TYPE_S];
  int i;
  int split = 6;

  if (begin < 3)
    {
      /* Always split before and after MMF.  */
      if (p->t[0] == TYPE_M && p->t[1] == TYPE_M && p->t[2] == TYPE_F)
	return 3;
      if (p->t[3] == TYPE_M && p->t[4] == TYPE_M && p->t[5] == TYPE_F)
	return 3;
      /* Always split after MBB and BBB.  */
      if (p->t[1] == TYPE_B)
	return 3;
      /* Split after first bundle in MIB BBB combination.  */
      if (p->t[2] == TYPE_B && p->t[3] == TYPE_B)
	return 3;
    }

  memset (type_count, 0, sizeof type_count);
  for (i = begin; i < split; i++)
    {
      enum attr_type t0 = p->t[i];
      /* An MLX bundle reserves the same units as an MFI bundle.  */
      enum attr_type t = (t0 == TYPE_L ? TYPE_F
			  : t0 == TYPE_X ? TYPE_I
			  : t0);
      int max = (t == TYPE_B ? 3 : t == TYPE_F ? 1 : 2);
      if (type_count[t] == max)
	return i;
      type_count[t]++;
    }
  return split;
}

/* Return the maximum number of instructions a cpu can issue.  */

int
ia64_issue_rate ()
{
  return 6;
}

/* Helper function - like single_set, but look inside COND_EXEC.  */

static rtx
ia64_single_set (insn)
     rtx insn;
{
  rtx x = PATTERN (insn);
  if (GET_CODE (x) == COND_EXEC)
    x = COND_EXEC_CODE (x);
  if (GET_CODE (x) == SET)
    return x;
  return single_set_2 (insn, x);
}

/* Adjust the cost of a scheduling dependency.  Return the new cost of
   a dependency LINK or INSN on DEP_INSN.  COST is the current cost.  */

int
ia64_adjust_cost (insn, link, dep_insn, cost)
     rtx insn, link, dep_insn;
     int cost;
{
  enum attr_type dep_type;
  enum attr_itanium_class dep_class;
  enum attr_itanium_class insn_class;
  rtx dep_set, set, src, addr;

  if (GET_CODE (PATTERN (insn)) == CLOBBER
      || GET_CODE (PATTERN (insn)) == USE
      || GET_CODE (PATTERN (dep_insn)) == CLOBBER
      || GET_CODE (PATTERN (dep_insn)) == USE
      /* @@@ Not accurate for indirect calls.  */
      || GET_CODE (insn) == CALL_INSN
      || ia64_safe_type (insn) == TYPE_S)
    return 0;

  if (REG_NOTE_KIND (link) == REG_DEP_OUTPUT
      || REG_NOTE_KIND (link) == REG_DEP_ANTI)
    return 0;

  dep_type = ia64_safe_type (dep_insn);
  dep_class = ia64_safe_itanium_class (dep_insn);
  insn_class = ia64_safe_itanium_class (insn);

  /* Compares that feed a conditional branch can execute in the same
     cycle.  */
  dep_set = ia64_single_set (dep_insn);
  set = ia64_single_set (insn);

  if (dep_type != TYPE_F
      && dep_set
      && GET_CODE (SET_DEST (dep_set)) == REG
      && PR_REG (REGNO (SET_DEST (dep_set)))
      && GET_CODE (insn) == JUMP_INSN)
    return 0;

  if (dep_set && GET_CODE (SET_DEST (dep_set)) == MEM)
    {
      /* ??? Can't find any information in the documenation about whether
	 a sequence
	   st [rx] = ra
	   ld rb = [ry]
	 splits issue.  Assume it doesn't.  */
      return 0;
    }

  src = set ? SET_SRC (set) : 0;
  addr = 0;
  if (set && GET_CODE (SET_DEST (set)) == MEM)
    addr = XEXP (SET_DEST (set), 0);
  else if (set && GET_CODE (src) == MEM)
    addr = XEXP (src, 0);
  else if (set && GET_CODE (src) == ZERO_EXTEND
	   && GET_CODE (XEXP (src, 0)) == MEM)
    addr = XEXP (XEXP (src, 0), 0);
  else if (set && GET_CODE (src) == UNSPEC
	   && XVECLEN (XEXP (src, 0), 0) > 0
	   && GET_CODE (XVECEXP (src, 0, 0)) == MEM)
    addr = XEXP (XVECEXP (src, 0, 0), 0);
  if (addr && GET_CODE (addr) == POST_MODIFY)
    addr = XEXP (addr, 0);

  set = ia64_single_set (dep_insn);

  if ((dep_class == ITANIUM_CLASS_IALU
       || dep_class == ITANIUM_CLASS_ILOG
       || dep_class == ITANIUM_CLASS_LD)
      && (insn_class == ITANIUM_CLASS_LD
	  || insn_class == ITANIUM_CLASS_ST))
    {
      if (! addr || ! set)
	abort ();
      /* This isn't completely correct - an IALU that feeds an address has
	 a latency of 1 cycle if it's issued in an M slot, but 2 cycles
	 otherwise.  Unfortunately there's no good way to describe this.  */
      if (reg_overlap_mentioned_p (SET_DEST (set), addr))
	return cost + 1;
    }
  if ((dep_class == ITANIUM_CLASS_IALU
       || dep_class == ITANIUM_CLASS_ILOG
       || dep_class == ITANIUM_CLASS_LD)
      && (insn_class == ITANIUM_CLASS_MMMUL
	  || insn_class == ITANIUM_CLASS_MMSHF
	  || insn_class == ITANIUM_CLASS_MMSHFI))
    return 3;
  if (dep_class == ITANIUM_CLASS_FMAC
      && (insn_class == ITANIUM_CLASS_FMISC
	  || insn_class == ITANIUM_CLASS_FCVTFX
	  || insn_class == ITANIUM_CLASS_XMPY))
    return 7;
  if ((dep_class == ITANIUM_CLASS_FMAC
       || dep_class == ITANIUM_CLASS_FMISC
       || dep_class == ITANIUM_CLASS_FCVTFX
       || dep_class == ITANIUM_CLASS_XMPY)
      && insn_class == ITANIUM_CLASS_STF)
    return 8;
  if ((dep_class == ITANIUM_CLASS_MMMUL
       || dep_class == ITANIUM_CLASS_MMSHF
       || dep_class == ITANIUM_CLASS_MMSHFI)
      && (insn_class == ITANIUM_CLASS_LD
	  || insn_class == ITANIUM_CLASS_ST
	  || insn_class == ITANIUM_CLASS_IALU
	  || insn_class == ITANIUM_CLASS_ILOG
	  || insn_class == ITANIUM_CLASS_ISHF))
    return 4;

  return cost;
}

/* Describe the current state of the Itanium pipeline.  */
static struct
{
  /* The first slot that is used in the current cycle.  */
  int first_slot;
  /* The next slot to fill.  */
  int cur;
  /* The packet we have selected for the current issue window.  */
  const struct ia64_packet *packet;
  /* The position of the split issue that occurs due to issue width
     limitations (6 if there's no split issue).  */
  int split;
  /* Record data about the insns scheduled so far in the same issue
     window.  The elements up to but not including FIRST_SLOT belong
     to the previous cycle, the ones starting with FIRST_SLOT belong
     to the current cycle.  */
  enum attr_type types[6];
  rtx insns[6];
  int stopbit[6];
  /* Nonzero if we decided to schedule a stop bit.  */
  int last_was_stop;
} sched_data;

/* Temporary arrays; they have enough elements to hold all insns that
   can be ready at the same time while scheduling of the current block.
   SCHED_READY can hold ready insns, SCHED_TYPES their types.  */
static rtx *sched_ready;
static enum attr_type *sched_types;

/* Determine whether an insn INSN of type ITYPE can fit into slot SLOT
   of packet P.  */

static int
insn_matches_slot (p, itype, slot, insn)
     const struct ia64_packet *p;
     enum attr_type itype;
     int slot;
     rtx insn;
{
  enum attr_itanium_requires_unit0 u0;
  enum attr_type stype = p->t[slot];

  if (insn)
    {
      u0 = ia64_safe_itanium_requires_unit0 (insn);
      if (u0 == ITANIUM_REQUIRES_UNIT0_YES)
	{
	  int i;
	  for (i = sched_data.first_slot; i < slot; i++)
	    if (p->t[i] == stype)
	      return 0;
	}
      if (GET_CODE (insn) == CALL_INSN)
	{
	  /* Reject calls in multiway branch packets.  We want to limit
	     the number of multiway branches we generate (since the branch
	     predictor is limited), and this seems to work fairly well.
	     (If we didn't do this, we'd have to add another test here to
	     force calls into the third slot of the bundle.)  */
	  if (slot < 3)
	    {
	      if (p->t[1] == TYPE_B)
		return 0;
	    }
	  else
	    {
	      if (p->t[4] == TYPE_B)
		return 0;
	    }
	}
    }

  if (itype == stype)
    return 1;
  if (itype == TYPE_A)
    return stype == TYPE_M || stype == TYPE_I;
  return 0;
}

/* Like emit_insn_before, but skip cycle_display insns.  This makes the
   assembly output a bit prettier.  */

static void
ia64_emit_insn_before (insn, before)
     rtx insn, before;
{
  rtx prev = PREV_INSN (before);
  if (prev && GET_CODE (prev) == INSN
      && GET_CODE (PATTERN (prev)) == UNSPEC
      && XINT (PATTERN (prev), 1) == 23)
    before = prev;
  emit_insn_before (insn, before);
}

#if 0
/* Generate a nop insn of the given type.  Note we never generate L type
   nops.  */

static rtx
gen_nop_type (t)
     enum attr_type t;
{
  switch (t)
    {
    case TYPE_M:
      return gen_nop_m ();
    case TYPE_I:
      return gen_nop_i ();
    case TYPE_B:
      return gen_nop_b ();
    case TYPE_F:
      return gen_nop_f ();
    case TYPE_X:
      return gen_nop_x ();
    default:
      abort ();
    }
}
#endif

/* When rotating a bundle out of the issue window, insert a bundle selector
   insn in front of it.  DUMP is the scheduling dump file or NULL.  START
   is either 0 or 3, depending on whether we want to emit a bundle selector
   for the first bundle or the second bundle in the current issue window.

   The selector insns are emitted this late because the selected packet can
   be changed until parts of it get rotated out.  */

static void
finish_last_head (dump, start)
     FILE *dump;
     int start;
{
  const struct ia64_packet *p = sched_data.packet;
  const struct bundle *b = start == 0 ? p->t1 : p->t2;
  int bundle_type = b - bundle;
  rtx insn;
  int i;

  if (! ia64_final_schedule)
    return;

  for (i = start; sched_data.insns[i] == 0; i++)
    if (i == start + 3)
      abort ();
  insn = sched_data.insns[i];

  if (dump)
    fprintf (dump, "//    Emitting template before %d: %s\n",
	     INSN_UID (insn), b->name);

  ia64_emit_insn_before (gen_bundle_selector (GEN_INT (bundle_type)), insn);
}

/* We can't schedule more insns this cycle.  Fix up the scheduling state
   and advance FIRST_SLOT and CUR.
   We have to distribute the insns that are currently found between
   FIRST_SLOT and CUR into the slots of the packet we have selected.  So
   far, they are stored successively in the fields starting at FIRST_SLOT;
   now they must be moved to the correct slots.
   DUMP is the current scheduling dump file, or NULL.  */

static void
cycle_end_fill_slots (dump)
     FILE *dump;
{
  const struct ia64_packet *packet = sched_data.packet;
  int slot, i;
  enum attr_type tmp_types[6];
  rtx tmp_insns[6];

  memcpy (tmp_types, sched_data.types, 6 * sizeof (enum attr_type));
  memcpy (tmp_insns, sched_data.insns, 6 * sizeof (rtx));

  for (i = slot = sched_data.first_slot; i < sched_data.cur; i++)
    {
      enum attr_type t = tmp_types[i];
      if (t != ia64_safe_type (tmp_insns[i]))
	abort ();
      while (! insn_matches_slot (packet, t, slot, tmp_insns[i]))
	{
	  if (slot > sched_data.split)
	    abort ();
	  if (dump)
	    fprintf (dump, "// Packet needs %s, have %s\n", type_names[packet->t[slot]],
		     type_names[t]);
	  sched_data.types[slot] = packet->t[slot];
	  sched_data.insns[slot] = 0;
	  sched_data.stopbit[slot] = 0;
	  slot++;
	}
      /* Do _not_ use T here.  If T == TYPE_A, then we'd risk changing the
	 actual slot type later.  */
      sched_data.types[slot] = packet->t[slot];
      sched_data.insns[slot] = tmp_insns[i];
      sched_data.stopbit[slot] = 0;
      slot++;
    }

  /* This isn't right - there's no need to pad out until the forced split;
     the CPU will automatically split if an insn isn't ready.  */
#if 0
  while (slot < sched_data.split)
    {
      sched_data.types[slot] = packet->t[slot];
      sched_data.insns[slot] = 0;
      sched_data.stopbit[slot] = 0;
      slot++;
    }
#endif

  sched_data.first_slot = sched_data.cur = slot;
}

/* Bundle rotations, as described in the Itanium optimization manual.
   We can rotate either one or both bundles out of the issue window.
   DUMP is the current scheduling dump file, or NULL.  */

static void
rotate_one_bundle (dump)
     FILE *dump;
{
  if (dump)
    fprintf (dump, "// Rotating one bundle.\n");

  finish_last_head (dump, 0);
  if (sched_data.cur > 3)
    {
      sched_data.cur -= 3;
      sched_data.first_slot -= 3;
      memmove (sched_data.types,
	       sched_data.types + 3,
	       sched_data.cur * sizeof *sched_data.types);
      memmove (sched_data.stopbit,
	       sched_data.stopbit + 3,
	       sched_data.cur * sizeof *sched_data.stopbit);
      memmove (sched_data.insns,
	       sched_data.insns + 3,
	       sched_data.cur * sizeof *sched_data.insns);
    }
  else
    {
      sched_data.cur = 0;
      sched_data.first_slot = 0;
    }
}

static void
rotate_two_bundles (dump)
     FILE *dump;
{
  if (dump)
    fprintf (dump, "// Rotating two bundles.\n");

  if (sched_data.cur == 0)
    return;

  finish_last_head (dump, 0);
  if (sched_data.cur > 3)
    finish_last_head (dump, 3);
  sched_data.cur = 0;
  sched_data.first_slot = 0;
}

/* We're beginning a new block.  Initialize data structures as necessary.  */

void
ia64_sched_init (dump, sched_verbose, max_ready)
     FILE *dump ATTRIBUTE_UNUSED;
     int sched_verbose ATTRIBUTE_UNUSED;
     int max_ready;
{
  static int initialized = 0;

  if (! initialized)
    {
      int b1, b2, i;

      initialized = 1;

      for (i = b1 = 0; b1 < NR_BUNDLES; b1++)
	{
	  const struct bundle *t1 = bundle + b1;
	  for (b2 = 0; b2 < NR_BUNDLES; b2++, i++)
	    {
	      const struct bundle *t2 = bundle + b2;

	      packets[i].t1 = t1;
	      packets[i].t2 = t2;
	    }
	}
      for (i = 0; i < NR_PACKETS; i++)
	{
	  int j;
	  for (j = 0; j < 3; j++)
	    packets[i].t[j] = packets[i].t1->t[j];
	  for (j = 0; j < 3; j++)
	    packets[i].t[j + 3] = packets[i].t2->t[j];
	  packets[i].first_split = itanium_split_issue (packets + i, 0);
	}
	
    }

  init_insn_group_barriers ();

  memset (&sched_data, 0, sizeof sched_data);
  sched_types = (enum attr_type *) xmalloc (max_ready
					    * sizeof (enum attr_type));
  sched_ready = (rtx *) xmalloc (max_ready * sizeof (rtx));
}

/* See if the packet P can match the insns we have already scheduled.  Return
   nonzero if so.  In *PSLOT, we store the first slot that is available for
   more instructions if we choose this packet.
   SPLIT holds the last slot we can use, there's a split issue after it so
   scheduling beyond it would cause us to use more than one cycle.  */

static int
packet_matches_p (p, split, pslot)
     const struct ia64_packet *p;
     int split;
     int *pslot;
{
  int filled = sched_data.cur;
  int first = sched_data.first_slot;
  int i, slot;

  /* First, check if the first of the two bundles must be a specific one (due
     to stop bits).  */
  if (first > 0 && sched_data.stopbit[0] && p->t1->possible_stop != 1)
    return 0;
  if (first > 1 && sched_data.stopbit[1] && p->t1->possible_stop != 2)
    return 0;

  for (i = 0; i < first; i++)
    if (! insn_matches_slot (p, sched_data.types[i], i,
			     sched_data.insns[i]))
      return 0;
  for (i = slot = first; i < filled; i++)
    {
      while (slot < split)
	{
	  if (insn_matches_slot (p, sched_data.types[i], slot,
				 sched_data.insns[i]))
	    break;
	  slot++;
	}
      if (slot == split)
	return 0;
      slot++;
    }

  if (pslot)
    *pslot = slot;
  return 1;
}

/* A frontend for itanium_split_issue.  For a packet P and a slot
   number FIRST that describes the start of the current clock cycle,
   return the slot number of the first split issue.  This function
   uses the cached number found in P if possible.  */

static int
get_split (p, first)
     const struct ia64_packet *p;
     int first;
{
  if (first == 0)
    return p->first_split;
  return itanium_split_issue (p, first);
}

/* Given N_READY insns in the array READY, whose types are found in the
   corresponding array TYPES, return the insn that is best suited to be
   scheduled in slot SLOT of packet P.  */

static int
find_best_insn (ready, types, n_ready, p, slot)
     rtx *ready;
     enum attr_type *types;
     int n_ready;
     const struct ia64_packet *p;
     int slot;
{
  int best = -1;
  int best_pri = 0;
  while (n_ready-- > 0)
    {
      rtx insn = ready[n_ready];
      if (! insn)
	continue;
      if (best >= 0 && INSN_PRIORITY (ready[n_ready]) < best_pri)
	break;
      /* If we have equally good insns, one of which has a stricter
	 slot requirement, prefer the one with the stricter requirement.  */
      if (best >= 0 && types[n_ready] == TYPE_A)
	continue;
      if (insn_matches_slot (p, types[n_ready], slot, insn))
	{
	  best = n_ready;
	  best_pri = INSN_PRIORITY (ready[best]);

	  /* If there's no way we could get a stricter requirement, stop
	     looking now.  */
	  if (types[n_ready] != TYPE_A
	      && ia64_safe_itanium_requires_unit0 (ready[n_ready]))
	    break;
	  break;
	}
    }
  return best;
}

/* Select the best packet to use given the current scheduler state and the
   current ready list.
   READY is an array holding N_READY ready insns; TYPES is a corresponding
   array that holds their types.  Store the best packet in *PPACKET and the
   number of insns that can be scheduled in the current cycle in *PBEST.  */

static void
find_best_packet (pbest, ppacket, ready, types, n_ready)
     int *pbest;
     const struct ia64_packet **ppacket;
     rtx *ready;
     enum attr_type *types;
     int n_ready;
{
  int first = sched_data.first_slot;
  int best = 0;
  int lowest_end = 6;
  const struct ia64_packet *best_packet = NULL;
  int i;

  for (i = 0; i < NR_PACKETS; i++)
    {
      const struct ia64_packet *p = packets + i;
      int slot;
      int split = get_split (p, first);
      int win = 0;
      int first_slot, last_slot;
      int b_nops = 0;

      if (! packet_matches_p (p, split, &first_slot))
	continue;

      memcpy (sched_ready, ready, n_ready * sizeof (rtx));

      win = 0;
      last_slot = 6;
      for (slot = first_slot; slot < split; slot++)
	{
	  int insn_nr;

	  /* Disallow a degenerate case where the first bundle doesn't
	     contain anything but NOPs!  */
	  if (first_slot == 0 && win == 0 && slot == 3)
	    {
	      win = -1;
	      break;
	    }

	  insn_nr = find_best_insn (sched_ready, types, n_ready, p, slot);
	  if (insn_nr >= 0)
	    {
	      sched_ready[insn_nr] = 0;
	      last_slot = slot;
	      win++;
	    }
	  else if (p->t[slot] == TYPE_B)
	    b_nops++;
	}
      /* We must disallow MBB/BBB packets if any of their B slots would be
	 filled with nops.  */
      if (last_slot < 3)
	{
	  if (p->t[1] == TYPE_B && (b_nops || last_slot < 2))
	    win = -1;
	}
      else
	{
	  if (p->t[4] == TYPE_B && (b_nops || last_slot < 5))
	    win = -1;
	}

      if (win > best
	  || (win == best && last_slot < lowest_end))
	{
	  best = win;
	  lowest_end = last_slot;
	  best_packet = p;
	}
    }
  *pbest = best;
  *ppacket = best_packet;
}

/* Reorder the ready list so that the insns that can be issued in this cycle
   are found in the correct order at the end of the list.
   DUMP is the scheduling dump file, or NULL.  READY points to the start,
   E_READY to the end of the ready list.  MAY_FAIL determines what should be
   done if no insns can be scheduled in this cycle: if it is zero, we abort,
   otherwise we return 0.
   Return 1 if any insns can be scheduled in this cycle.  */

static int
itanium_reorder (dump, ready, e_ready, may_fail)
     FILE *dump;
     rtx *ready;
     rtx *e_ready;
     int may_fail;
{
  const struct ia64_packet *best_packet;
  int n_ready = e_ready - ready;
  int first = sched_data.first_slot;
  int i, best, best_split, filled;

  for (i = 0; i < n_ready; i++)
    sched_types[i] = ia64_safe_type (ready[i]);

  find_best_packet (&best, &best_packet, ready, sched_types, n_ready);

  if (best == 0)
    {
      if (may_fail)
	return 0;
      abort ();
    }

  if (dump)
    {
      fprintf (dump, "// Selected bundles: %s %s (%d insns)\n",
	       best_packet->t1->name,
	       best_packet->t2 ? best_packet->t2->name : NULL, best);
    }

  best_split = itanium_split_issue (best_packet, first);
  packet_matches_p (best_packet, best_split, &filled);

  for (i = filled; i < best_split; i++)
    {
      int insn_nr;

      insn_nr = find_best_insn (ready, sched_types, n_ready, best_packet, i);
      if (insn_nr >= 0)
	{
	  rtx insn = ready[insn_nr];
	  memmove (ready + insn_nr, ready + insn_nr + 1,
		   (n_ready - insn_nr - 1) * sizeof (rtx));
	  memmove (sched_types + insn_nr, sched_types + insn_nr + 1,
		   (n_ready - insn_nr - 1) * sizeof (enum attr_type));
	  ready[--n_ready] = insn;
	}
    }

  sched_data.packet = best_packet;
  sched_data.split = best_split;
  return 1;
}

/* Dump information about the current scheduling state to file DUMP.  */

static void
dump_current_packet (dump)
     FILE *dump;
{
  int i;
  fprintf (dump, "//    %d slots filled:", sched_data.cur);
  for (i = 0; i < sched_data.first_slot; i++)
    {
      rtx insn = sched_data.insns[i];
      fprintf (dump, " %s", type_names[sched_data.types[i]]);
      if (insn)
	fprintf (dump, "/%s", type_names[ia64_safe_type (insn)]);
      if (sched_data.stopbit[i])
	fprintf (dump, " ;;");
    }
  fprintf (dump, " :::");
  for (i = sched_data.first_slot; i < sched_data.cur; i++)
    {
      rtx insn = sched_data.insns[i];
      enum attr_type t = ia64_safe_type (insn);
      fprintf (dump, " (%d) %s", INSN_UID (insn), type_names[t]);
    }
  fprintf (dump, "\n");
}

/* Schedule a stop bit.  DUMP is the current scheduling dump file, or
   NULL.  */

static void
schedule_stop (dump)
     FILE *dump;
{
  const struct ia64_packet *best = sched_data.packet;
  int i;
  int best_stop = 6;

  if (dump)
    fprintf (dump, "// Stop bit, cur = %d.\n", sched_data.cur);

  if (sched_data.cur == 0)
    {
      if (dump)
	fprintf (dump, "//   At start of bundle, so nothing to do.\n");

      rotate_two_bundles (NULL);
      return;
    }

  for (i = -1; i < NR_PACKETS; i++)
    {
      /* This is a slight hack to give the current packet the first chance.
	 This is done to avoid e.g. switching from MIB to MBB bundles.  */
      const struct ia64_packet *p = (i >= 0 ? packets + i : sched_data.packet);
      int split = get_split (p, sched_data.first_slot);
      const struct bundle *compare;
      int next, stoppos;

      if (! packet_matches_p (p, split, &next))
	continue;

      compare = next > 3 ? p->t2 : p->t1;

      stoppos = 3;
      if (compare->possible_stop)
	stoppos = compare->possible_stop;
      if (next > 3)
	stoppos += 3;

      if (stoppos < next || stoppos >= best_stop)
	{
	  if (compare->possible_stop == 0)
	    continue;
	  stoppos = (next > 3 ? 6 : 3);
	}
      if (stoppos < next || stoppos >= best_stop)
	continue;

      if (dump)
	fprintf (dump, "//   switching from %s %s to %s %s (stop at %d)\n",
		 best->t1->name, best->t2->name, p->t1->name, p->t2->name,
		 stoppos);

      best_stop = stoppos;
      best = p;
    }

  sched_data.packet = best;
  cycle_end_fill_slots (dump);
  while (sched_data.cur < best_stop)
    {
      sched_data.types[sched_data.cur] = best->t[sched_data.cur];
      sched_data.insns[sched_data.cur] = 0;
      sched_data.stopbit[sched_data.cur] = 0;
      sched_data.cur++;
    }
  sched_data.stopbit[sched_data.cur - 1] = 1;
  sched_data.first_slot = best_stop;

  if (dump)
    dump_current_packet (dump);
}

/* If necessary, perform one or two rotations on the scheduling state.  
   This should only be called if we are starting a new cycle.  */

static void
maybe_rotate (dump)
     FILE *dump;
{
  if (sched_data.cur == 6)
    rotate_two_bundles (dump);
  else if (sched_data.cur >= 3)
    rotate_one_bundle (dump);
  sched_data.first_slot = sched_data.cur;
}

/* We are about to being issuing insns for this clock cycle.
   Override the default sort algorithm to better slot instructions.  */

int
ia64_sched_reorder (dump, sched_verbose, ready, pn_ready, reorder_type)
     FILE *dump ATTRIBUTE_UNUSED;
     int sched_verbose ATTRIBUTE_UNUSED;
     rtx *ready;
     int *pn_ready;
     int reorder_type;
{
  int n_ready = *pn_ready;
  rtx *e_ready = ready + n_ready;
  rtx *insnp;
  rtx highest;

  if (sched_verbose)
    {
      fprintf (dump, "// ia64_sched_reorder (type %d):\n", reorder_type);
      dump_current_packet (dump);
    }

  if (reorder_type == 0)
    maybe_rotate (sched_verbose ? dump : NULL);

  /* First, move all USEs, CLOBBERs and other crud out of the way.  */
  highest = ready[n_ready - 1];
  for (insnp = ready; insnp < e_ready; insnp++)
    if (insnp < e_ready)
      {
	rtx insn = *insnp;
	enum attr_type t = ia64_safe_type (insn);
	if (t == TYPE_UNKNOWN)
	  {
	    highest = ready[n_ready - 1];
	    ready[n_ready - 1] = insn;
	    *insnp = highest;
	    if (ia64_final_schedule && group_barrier_needed_p (insn))
	      {
		schedule_stop (sched_verbose ? dump : NULL);
		sched_data.last_was_stop = 1;
		maybe_rotate (sched_verbose ? dump : NULL);
	      }
	    else if (GET_CODE (PATTERN (insn)) == ASM_INPUT
		     || asm_noperands (PATTERN (insn)) >= 0)
	      {
		/* It must be an asm of some kind.  */
		cycle_end_fill_slots (sched_verbose ? dump : NULL);
	      }
	    return 1;
	  }
      }

  if (ia64_final_schedule)
    {
      int nr_need_stop = 0;

      for (insnp = ready; insnp < e_ready; insnp++)
	if (safe_group_barrier_needed_p (*insnp))
	  nr_need_stop++;

      /* Schedule a stop bit if
          - all insns require a stop bit, or
          - we are starting a new cycle and _any_ insns require a stop bit.
         The reason for the latter is that if our schedule is accurate, then
         the additional stop won't decrease performance at this point (since
	 there's a split issue at this point anyway), but it gives us more
         freedom when scheduling the currently ready insns.  */
      if ((reorder_type == 0 && nr_need_stop)
	  || (reorder_type == 1 && n_ready == nr_need_stop))
	{
	  schedule_stop (sched_verbose ? dump : NULL);
	  sched_data.last_was_stop = 1;
	  maybe_rotate (sched_verbose ? dump : NULL);
	  if (reorder_type == 1)
	    return 0;
	}
      else
	{
	  int deleted = 0;
	  insnp = e_ready;
	  /* Move down everything that needs a stop bit, preserving relative
	     order.  */
	  while (insnp-- > ready + deleted)
	    while (insnp >= ready + deleted)
	      {
		rtx insn = *insnp;
		if (! safe_group_barrier_needed_p (insn))
		  break;
		memmove (ready + 1, ready, (insnp - ready) * sizeof (rtx));
		*ready = insn;
		deleted++;
	      }
	  n_ready -= deleted;
	  ready += deleted;
	  if (deleted != nr_need_stop)
	    abort ();
	}
    }

  return itanium_reorder (sched_verbose ? dump : NULL,
			  ready, e_ready, reorder_type == 1);
}

/* Like ia64_sched_reorder, but called after issuing each insn.
   Override the default sort algorithm to better slot instructions.  */

int
ia64_sched_reorder2 (dump, sched_verbose, ready, pn_ready, clock_var)
     FILE *dump ATTRIBUTE_UNUSED;
     int sched_verbose ATTRIBUTE_UNUSED;
     rtx *ready;
     int *pn_ready;
     int clock_var ATTRIBUTE_UNUSED;
{
  if (sched_data.last_was_stop)
    return 0;

  /* Detect one special case and try to optimize it.
     If we have 1.M;;MI 2.MIx, and slots 2.1 (M) and 2.2 (I) are both NOPs,
     then we can get better code by transforming this to 1.MFB;; 2.MIx.  */
  if (sched_data.first_slot == 1
      && sched_data.stopbit[0]
      && ((sched_data.cur == 4
	   && (sched_data.types[1] == TYPE_M || sched_data.types[1] == TYPE_A)
	   && (sched_data.types[2] == TYPE_I || sched_data.types[2] == TYPE_A)
	   && (sched_data.types[3] != TYPE_M && sched_data.types[3] != TYPE_A))
	  || (sched_data.cur == 3
	      && (sched_data.types[1] == TYPE_M || sched_data.types[1] == TYPE_A)
	      && (sched_data.types[2] != TYPE_M && sched_data.types[2] != TYPE_I
		  && sched_data.types[2] != TYPE_A))))
      
    {
      int i, best;
      rtx stop = PREV_INSN (sched_data.insns[1]);
      rtx pat;

      sched_data.stopbit[0] = 0;
      sched_data.stopbit[2] = 1;
      if (GET_CODE (stop) != INSN)
	abort ();

      pat = PATTERN (stop);
      /* Ignore cycle displays.  */
      if (GET_CODE (pat) == UNSPEC && XINT (pat, 1) == 23)
	stop = PREV_INSN (stop);
      pat = PATTERN (stop);
      if (GET_CODE (pat) != UNSPEC_VOLATILE
	  || XINT (pat, 1) != 2
	  || INTVAL (XVECEXP (pat, 0, 0)) != 1)
	abort ();
      XVECEXP (pat, 0, 0) = GEN_INT (3);

      sched_data.types[5] = sched_data.types[3];
      sched_data.types[4] = sched_data.types[2];
      sched_data.types[3] = sched_data.types[1];
      sched_data.insns[5] = sched_data.insns[3];
      sched_data.insns[4] = sched_data.insns[2];
      sched_data.insns[3] = sched_data.insns[1];
      sched_data.stopbit[5] = sched_data.stopbit[4] = sched_data.stopbit[3] = 0;
      sched_data.cur += 2;
      sched_data.first_slot = 3;
      for (i = 0; i < NR_PACKETS; i++)
	{
	  const struct ia64_packet *p = packets + i;
	  if (p->t[0] == TYPE_M && p->t[1] == TYPE_F && p->t[2] == TYPE_B)
	    {
	      sched_data.packet = p;
	      break;
	    }
	}
      rotate_one_bundle (sched_verbose ? dump : NULL);

      best = 6;
      for (i = 0; i < NR_PACKETS; i++)
	{
	  const struct ia64_packet *p = packets + i;
	  int split = get_split (p, sched_data.first_slot);
	  int next;

	  /* Disallow multiway branches here.  */
	  if (p->t[1] == TYPE_B)
	    continue;

	  if (packet_matches_p (p, split, &next) && next < best)
	    {
	      best = next;
	      sched_data.packet = p;
	      sched_data.split = split;
	    }
	}
      if (best == 6)
	abort ();
    }

  if (*pn_ready > 0)
    {
      int more = ia64_sched_reorder (dump, sched_verbose, ready, pn_ready, 1);
      if (more)
	return more;
      /* Did we schedule a stop?  If so, finish this cycle.  */
      if (sched_data.cur == sched_data.first_slot)
	return 0;
    }

  if (sched_verbose)
    fprintf (dump, "//   Can't issue more this cycle; updating type array.\n");

  cycle_end_fill_slots (sched_verbose ? dump : NULL);
  if (sched_verbose)
    dump_current_packet (dump);
  return 0;
}

/* We are about to issue INSN.  Return the number of insns left on the
   ready queue that can be issued this cycle.  */

int
ia64_variable_issue (dump, sched_verbose, insn, can_issue_more)
     FILE *dump;
     int sched_verbose;
     rtx insn;
     int can_issue_more ATTRIBUTE_UNUSED;
{
  enum attr_type t = ia64_safe_type (insn);

  if (sched_data.last_was_stop)
    {
      int t = sched_data.first_slot;
      if (t == 0)
	t = 3;
      ia64_emit_insn_before (gen_insn_group_barrier (GEN_INT (t)), insn);
      init_insn_group_barriers ();
      sched_data.last_was_stop = 0;
    }

  if (t == TYPE_UNKNOWN)
    {
      if (sched_verbose)
	fprintf (dump, "// Ignoring type %s\n", type_names[t]);
      if (GET_CODE (PATTERN (insn)) == ASM_INPUT
	  || asm_noperands (PATTERN (insn)) >= 0)
	{
	  /* This must be some kind of asm.  Clear the scheduling state.  */
	  rotate_two_bundles (sched_verbose ? dump : NULL);
	  if (ia64_final_schedule)
	    group_barrier_needed_p (insn);
	}
      return 1;
    }

  /* This is _not_ just a sanity check.  group_barrier_needed_p will update
     important state info.  Don't delete this test.  */
  if (ia64_final_schedule
      && group_barrier_needed_p (insn))
    abort ();

  sched_data.stopbit[sched_data.cur] = 0;
  sched_data.insns[sched_data.cur] = insn;
  sched_data.types[sched_data.cur] = t;

  sched_data.cur++;
  if (sched_verbose)
    fprintf (dump, "// Scheduling insn %d of type %s\n",
	     INSN_UID (insn), type_names[t]);

  if (GET_CODE (insn) == CALL_INSN && ia64_final_schedule)
    {
      schedule_stop (sched_verbose ? dump : NULL);
      sched_data.last_was_stop = 1;
    }

  return 1;
}

/* Free data allocated by ia64_sched_init.  */

void
ia64_sched_finish (dump, sched_verbose)
     FILE *dump;
     int sched_verbose;
{
  if (sched_verbose)
    fprintf (dump, "// Finishing schedule.\n");
  rotate_two_bundles (NULL);
  free (sched_types);
  free (sched_ready);
}

/* Emit pseudo-ops for the assembler to describe predicate relations.
   At present this assumes that we only consider predicate pairs to
   be mutex, and that the assembler can deduce proper values from
   straight-line code.  */

static void
emit_predicate_relation_info ()
{
  int i;

  for (i = n_basic_blocks - 1; i >= 0; --i)
    {
      basic_block bb = BASIC_BLOCK (i);
      int r;
      rtx head = bb->head;

      /* We only need such notes at code labels.  */
      if (GET_CODE (head) != CODE_LABEL)
	continue;
      if (GET_CODE (NEXT_INSN (head)) == NOTE
	  && NOTE_LINE_NUMBER (NEXT_INSN (head)) == NOTE_INSN_BASIC_BLOCK)
	head = NEXT_INSN (head);

      for (r = PR_REG (0); r < PR_REG (64); r += 2)
	if (REGNO_REG_SET_P (bb->global_live_at_start, r))
	  {
	    rtx p = gen_rtx_REG (BImode, r);
	    rtx n = emit_insn_after (gen_pred_rel_mutex (p), head);
	    if (head == bb->end)
	      bb->end = n;
	    head = n;
	  }
    }

  /* Look for conditional calls that do not return, and protect predicate
     relations around them.  Otherwise the assembler will assume the call
     returns, and complain about uses of call-clobbered predicates after
     the call.  */
  for (i = n_basic_blocks - 1; i >= 0; --i)
    {
      basic_block bb = BASIC_BLOCK (i);
      rtx insn = bb->head;
      
      while (1)
	{
	  if (GET_CODE (insn) == CALL_INSN
	      && GET_CODE (PATTERN (insn)) == COND_EXEC
	      && find_reg_note (insn, REG_NORETURN, NULL_RTX))
	    {
	      rtx b = emit_insn_before (gen_safe_across_calls_all (), insn);
	      rtx a = emit_insn_after (gen_safe_across_calls_normal (), insn);
	      if (bb->head == insn)
		bb->head = b;
	      if (bb->end == insn)
		bb->end = a;
	    }
	  
	  if (insn == bb->end)
	    break;
	  insn = NEXT_INSN (insn);
	}
    }
}

/* Generate a NOP instruction of type T.  We will never generate L type
   nops.  */

static rtx
gen_nop_type (t)
     enum attr_type t;
{
  switch (t)
    {
    case TYPE_M:
      return gen_nop_m ();
    case TYPE_I:
      return gen_nop_i ();
    case TYPE_B:
      return gen_nop_b ();
    case TYPE_F:
      return gen_nop_f ();
    case TYPE_X:
      return gen_nop_x ();
    default:
      abort ();
    }
}

/* After the last scheduling pass, fill in NOPs.  It's easier to do this
   here than while scheduling.  */

static void
ia64_emit_nops ()
{
  rtx insn;
  const struct bundle *b = 0;
  int bundle_pos = 0;

  for (insn = get_insns (); insn; insn = NEXT_INSN (insn))
    {
      rtx pat;
      enum attr_type t;
      pat = INSN_P (insn) ? PATTERN (insn) : const0_rtx;
      if (GET_CODE (pat) == USE || GET_CODE (pat) == CLOBBER)
	continue;
      if ((GET_CODE (pat) == UNSPEC && XINT (pat, 1) == 22)
	  || GET_CODE (insn) == CODE_LABEL)
	{
	  if (b)
	    while (bundle_pos < 3)
	      {
		emit_insn_before (gen_nop_type (b->t[bundle_pos]), insn);
		bundle_pos++;
	      }
	  if (GET_CODE (insn) != CODE_LABEL)
	    b = bundle + INTVAL (XVECEXP (pat, 0, 0));
	  else
	    b = 0;
	  bundle_pos = 0;
	  continue;
	}
      else if (GET_CODE (pat) == UNSPEC_VOLATILE && XINT (pat, 1) == 2)
	{
	  int t = INTVAL (XVECEXP (pat, 0, 0));
	  if (b)
	    while (bundle_pos < t)
	      {
		emit_insn_before (gen_nop_type (b->t[bundle_pos]), insn);
		bundle_pos++;
	      }
	  continue;
	}

      if (bundle_pos == 3)
	b = 0;

      if (b && INSN_P (insn))
	{
	  t = ia64_safe_type (insn);
	  if (asm_noperands (PATTERN (insn)) >= 0
	      || GET_CODE (PATTERN (insn)) == ASM_INPUT)
	    {
	      while (bundle_pos < 3)
		{
		  emit_insn_before (gen_nop_type (b->t[bundle_pos]), insn);
		  bundle_pos++;
		}
	      continue;
	    }

	  if (t == TYPE_UNKNOWN)
	    continue;
	  while (bundle_pos < 3)
	    {
	      if (t == b->t[bundle_pos]
		  || (t == TYPE_A && (b->t[bundle_pos] == TYPE_M
				      || b->t[bundle_pos] == TYPE_I)))
		break;

	      emit_insn_before (gen_nop_type (b->t[bundle_pos]), insn);
	      bundle_pos++;
	    }
	  if (bundle_pos < 3)
	    bundle_pos++;
	}
    }
}

/* Perform machine dependent operations on the rtl chain INSNS.  */

void
ia64_reorg (insns)
     rtx insns;
{
  /* If optimizing, we'll have split before scheduling.  */
  if (optimize == 0)
    split_all_insns (0);

  /* Make sure the CFG and global_live_at_start are correct
     for emit_predicate_relation_info.  */
  find_basic_blocks (insns, max_reg_num (), NULL);
  life_analysis (insns, NULL, PROP_DEATH_NOTES);

  if (optimize)
    {
      ia64_final_schedule = 1;
      schedule_ebbs (rtl_dump_file);
      ia64_final_schedule = 0;

      /* This relies on the NOTE_INSN_BASIC_BLOCK notes to be in the same
	 place as they were during scheduling.  */
      emit_insn_group_barriers (rtl_dump_file, insns);
      ia64_emit_nops ();
    }
  else
    emit_all_insn_group_barriers (rtl_dump_file, insns);

  fixup_errata ();
  emit_predicate_relation_info ();
}

/* Return true if REGNO is used by the epilogue.  */

int
ia64_epilogue_uses (regno)
     int regno;
{
  /* When a function makes a call through a function descriptor, we
     will write a (potentially) new value to "gp".  After returning
     from such a call, we need to make sure the function restores the
     original gp-value, even if the function itself does not use the
     gp anymore.  */
  if (regno == R_GR (1)
      && TARGET_CONST_GP
      && !(TARGET_AUTO_PIC || TARGET_NO_PIC))
    return 1;

  /* For functions defined with the syscall_linkage attribute, all input
     registers are marked as live at all function exits.  This prevents the
     register allocator from using the input registers, which in turn makes it
     possible to restart a system call after an interrupt without having to
     save/restore the input registers.  This also prevents kernel data from
     leaking to application code.  */

  if (IN_REGNO_P (regno)
      && lookup_attribute ("syscall_linkage",
			   TYPE_ATTRIBUTES (TREE_TYPE (current_function_decl))))
    return 1;

  /* Conditional return patterns can't represent the use of `b0' as
     the return address, so we force the value live this way.  */
  if (regno == R_BR (0))
    return 1;

  if (regs_ever_live[AR_LC_REGNUM] && regno == AR_LC_REGNUM)
    return 1;
  if (! current_function_is_leaf && regno == AR_PFS_REGNUM)
    return 1;
  if (TEST_HARD_REG_BIT (current_frame_info.mask, AR_UNAT_REGNUM)
      && regno == AR_UNAT_REGNUM)
    return 1;

  return 0;
}

/* Return true if IDENTIFIER is a valid attribute for TYPE.  */

int
ia64_valid_type_attribute (type, attributes, identifier, args)
     tree type;
     tree attributes ATTRIBUTE_UNUSED;
     tree identifier;
     tree args;
{
  /* We only support an attribute for function calls.  */

  if (TREE_CODE (type) != FUNCTION_TYPE
      && TREE_CODE (type) != METHOD_TYPE)
    return 0;

  /* The "syscall_linkage" attribute says the callee is a system call entry
     point.  This affects ia64_epilogue_uses.  */

  if (is_attribute_p ("syscall_linkage", identifier))
    return args == NULL_TREE;

  return 0;
}

/* For ia64, SYMBOL_REF_FLAG set means that it is a function.

   We add @ to the name if this goes in small data/bss.  We can only put
   a variable in small data/bss if it is defined in this module or a module
   that we are statically linked with.  We can't check the second condition,
   but TREE_STATIC gives us the first one.  */

/* ??? If we had IPA, we could check the second condition.  We could support
   programmer added section attributes if the variable is not defined in this
   module.  */

/* ??? See the v850 port for a cleaner way to do this.  */

/* ??? We could also support own long data here.  Generating movl/add/ld8
   instead of addl,ld8/ld8.  This makes the code bigger, but should make the
   code faster because there is one less load.  This also includes incomplete
   types which can't go in sdata/sbss.  */

/* ??? See select_section.  We must put short own readonly variables in
   sdata/sbss instead of the more natural rodata, because we can't perform
   the DECL_READONLY_SECTION test here.  */

extern struct obstack * saveable_obstack;

void
ia64_encode_section_info (decl)
     tree decl;
{
  const char *symbol_str;

  if (TREE_CODE (decl) == FUNCTION_DECL)
    {
      SYMBOL_REF_FLAG (XEXP (DECL_RTL (decl), 0)) = 1;
      return;
    }

  /* Careful not to prod global register variables.  */
  if (TREE_CODE (decl) != VAR_DECL
      || GET_CODE (DECL_RTL (decl)) != MEM
      || GET_CODE (XEXP (DECL_RTL (decl), 0)) != SYMBOL_REF)
    return;
    
  symbol_str = XSTR (XEXP (DECL_RTL (decl), 0), 0);

  /* We assume that -fpic is used only to create a shared library (dso).
     With -fpic, no global data can ever be sdata.
     Without -fpic, global common uninitialized data can never be sdata, since
     it can unify with a real definition in a dso.  */
  /* ??? Actually, we can put globals in sdata, as long as we don't use gprel
     to access them.  The linker may then be able to do linker relaxation to
     optimize references to them.  Currently sdata implies use of gprel.  */
  /* We need the DECL_EXTERNAL check for C++.  static class data members get
     both TREE_STATIC and DECL_EXTERNAL set, to indicate that they are
     statically allocated, but the space is allocated somewhere else.  Such
     decls can not be own data.  */
  if (! TARGET_NO_SDATA
      && TREE_STATIC (decl) && ! DECL_EXTERNAL (decl)
      && ! (DECL_ONE_ONLY (decl) || DECL_WEAK (decl))
      && ! (TREE_PUBLIC (decl)
	    && (flag_pic
		|| (DECL_COMMON (decl)
		    && (DECL_INITIAL (decl) == 0
			|| DECL_INITIAL (decl) == error_mark_node))))
      /* Either the variable must be declared without a section attribute,
	 or the section must be sdata or sbss.  */
      && (DECL_SECTION_NAME (decl) == 0
	  || ! strcmp (TREE_STRING_POINTER (DECL_SECTION_NAME (decl)),
		       ".sdata")
	  || ! strcmp (TREE_STRING_POINTER (DECL_SECTION_NAME (decl)),
		       ".sbss")))
    {
      HOST_WIDE_INT size = int_size_in_bytes (TREE_TYPE (decl));

      /* If the variable has already been defined in the output file, then it
	 is too late to put it in sdata if it wasn't put there in the first
	 place.  The test is here rather than above, because if it is already
	 in sdata, then it can stay there.  */

      if (TREE_ASM_WRITTEN (decl))
	;

      /* If this is an incomplete type with size 0, then we can't put it in
	 sdata because it might be too big when completed.  */
      else if (size > 0
	       && size <= (HOST_WIDE_INT) ia64_section_threshold
	       && symbol_str[0] != SDATA_NAME_FLAG_CHAR)
	{
	  size_t len = strlen (symbol_str);
	  char *newstr = alloca (len + 1);
	  const char *string;

	  *newstr = SDATA_NAME_FLAG_CHAR;
	  memcpy (newstr + 1, symbol_str, len + 1);
	  
	  string = ggc_alloc_string (newstr, len + 1);
	  XSTR (XEXP (DECL_RTL (decl), 0), 0) = string;
	}
    }
  /* This decl is marked as being in small data/bss but it shouldn't
     be; one likely explanation for this is that the decl has been
     moved into a different section from the one it was in when
     ENCODE_SECTION_INFO was first called.  Remove the '@'.*/
  else if (symbol_str[0] == SDATA_NAME_FLAG_CHAR)
    {
      XSTR (XEXP (DECL_RTL (decl), 0), 0)
	= ggc_strdup (symbol_str + 1);
    }
}

/* Output assembly directives for prologue regions.  */

/* The current basic block number.  */

static int block_num;

/* True if we need a copy_state command at the start of the next block.  */

static int need_copy_state;

/* The function emits unwind directives for the start of an epilogue.  */

static void
process_epilogue ()
{
  /* If this isn't the last block of the function, then we need to label the
     current state, and copy it back in at the start of the next block.  */

  if (block_num != n_basic_blocks - 1)
    {
      fprintf (asm_out_file, "\t.label_state 1\n");
      need_copy_state = 1;
    }

  fprintf (asm_out_file, "\t.restore sp\n");
}

/* This function processes a SET pattern looking for specific patterns
   which result in emitting an assembly directive required for unwinding.  */

static int
process_set (asm_out_file, pat)
     FILE *asm_out_file;
     rtx pat;
{
  rtx src = SET_SRC (pat);
  rtx dest = SET_DEST (pat);
  int src_regno, dest_regno;

  /* Look for the ALLOC insn.  */
  if (GET_CODE (src) == UNSPEC_VOLATILE
      && XINT (src, 1) == 0
      && GET_CODE (dest) == REG)
    {
      dest_regno = REGNO (dest);

      /* If this isn't the final destination for ar.pfs, the alloc
	 shouldn't have been marked frame related.  */
      if (dest_regno != current_frame_info.reg_save_ar_pfs)
	abort ();

      fprintf (asm_out_file, "\t.save ar.pfs, r%d\n",
	       ia64_dbx_register_number (dest_regno));
      return 1;
    }

  /* Look for SP = .... */
  if (GET_CODE (dest) == REG && REGNO (dest) == STACK_POINTER_REGNUM)
    {
      if (GET_CODE (src) == PLUS)
        {
	  rtx op0 = XEXP (src, 0);
	  rtx op1 = XEXP (src, 1);
	  if (op0 == dest && GET_CODE (op1) == CONST_INT)
	    {
	      if (INTVAL (op1) < 0)
		{
		  fputs ("\t.fframe ", asm_out_file);
		  fprintf (asm_out_file, HOST_WIDE_INT_PRINT_DEC,
			   -INTVAL (op1));
		  fputc ('\n', asm_out_file);
		}
	      else
		process_epilogue ();
	    }
	  else
	    abort ();
	}
      else if (GET_CODE (src) == REG
	       && REGNO (src) == HARD_FRAME_POINTER_REGNUM)
	process_epilogue ();
      else
	abort ();

      return 1;
    }

  /* Register move we need to look at.  */
  if (GET_CODE (dest) == REG && GET_CODE (src) == REG)
    {
      src_regno = REGNO (src);
      dest_regno = REGNO (dest);

      switch (src_regno)
	{
	case BR_REG (0):
	  /* Saving return address pointer.  */
	  if (dest_regno != current_frame_info.reg_save_b0)
	    abort ();
	  fprintf (asm_out_file, "\t.save rp, r%d\n",
		   ia64_dbx_register_number (dest_regno));
	  return 1;

	case PR_REG (0):
	  if (dest_regno != current_frame_info.reg_save_pr)
	    abort ();
	  fprintf (asm_out_file, "\t.save pr, r%d\n",
		   ia64_dbx_register_number (dest_regno));
	  return 1;

	case AR_UNAT_REGNUM:
	  if (dest_regno != current_frame_info.reg_save_ar_unat)
	    abort ();
	  fprintf (asm_out_file, "\t.save ar.unat, r%d\n",
		   ia64_dbx_register_number (dest_regno));
	  return 1;

	case AR_LC_REGNUM:
	  if (dest_regno != current_frame_info.reg_save_ar_lc)
	    abort ();
	  fprintf (asm_out_file, "\t.save ar.lc, r%d\n",
		   ia64_dbx_register_number (dest_regno));
	  return 1;

	case STACK_POINTER_REGNUM:
	  if (dest_regno != HARD_FRAME_POINTER_REGNUM
	      || ! frame_pointer_needed)
	    abort ();
	  fprintf (asm_out_file, "\t.vframe r%d\n",
		   ia64_dbx_register_number (dest_regno));
	  return 1;

	default:
	  /* Everything else should indicate being stored to memory.  */
	  abort ();
	}
    }

  /* Memory store we need to look at.  */
  if (GET_CODE (dest) == MEM && GET_CODE (src) == REG)
    {
      long off;
      rtx base;
      const char *saveop;

      if (GET_CODE (XEXP (dest, 0)) == REG)
	{
	  base = XEXP (dest, 0);
	  off = 0;
	}
      else if (GET_CODE (XEXP (dest, 0)) == PLUS
	       && GET_CODE (XEXP (XEXP (dest, 0), 1)) == CONST_INT)
	{
	  base = XEXP (XEXP (dest, 0), 0);
	  off = INTVAL (XEXP (XEXP (dest, 0), 1));
	}
      else
	abort ();

      if (base == hard_frame_pointer_rtx)
	{
	  saveop = ".savepsp";
	  off = - off;
	}
      else if (base == stack_pointer_rtx)
	saveop = ".savesp";
      else
	abort ();

      src_regno = REGNO (src);
      switch (src_regno)
	{
	case BR_REG (0):
	  if (current_frame_info.reg_save_b0 != 0)
	    abort ();
	  fprintf (asm_out_file, "\t%s rp, %ld\n", saveop, off);
	  return 1;

	case PR_REG (0):
	  if (current_frame_info.reg_save_pr != 0)
	    abort ();
	  fprintf (asm_out_file, "\t%s pr, %ld\n", saveop, off);
	  return 1;

	case AR_LC_REGNUM:
	  if (current_frame_info.reg_save_ar_lc != 0)
	    abort ();
	  fprintf (asm_out_file, "\t%s ar.lc, %ld\n", saveop, off);
	  return 1;

	case AR_PFS_REGNUM:
	  if (current_frame_info.reg_save_ar_pfs != 0)
	    abort ();
	  fprintf (asm_out_file, "\t%s ar.pfs, %ld\n", saveop, off);
	  return 1;

	case AR_UNAT_REGNUM:
	  if (current_frame_info.reg_save_ar_unat != 0)
	    abort ();
	  fprintf (asm_out_file, "\t%s ar.unat, %ld\n", saveop, off);
	  return 1;

	case GR_REG (4):
	case GR_REG (5):
	case GR_REG (6):
	case GR_REG (7):
	  fprintf (asm_out_file, "\t.save.g 0x%x\n",
		   1 << (src_regno - GR_REG (4)));
	  return 1;

	case BR_REG (1):
	case BR_REG (2):
	case BR_REG (3):
	case BR_REG (4):
	case BR_REG (5):
	  fprintf (asm_out_file, "\t.save.b 0x%x\n",
		   1 << (src_regno - BR_REG (1)));
	  return 1;

	case FR_REG (2):
	case FR_REG (3):
	case FR_REG (4):
	case FR_REG (5):
	  fprintf (asm_out_file, "\t.save.f 0x%x\n",
		   1 << (src_regno - FR_REG (2)));
	  return 1;

	case FR_REG (16): case FR_REG (17): case FR_REG (18): case FR_REG (19):
	case FR_REG (20): case FR_REG (21): case FR_REG (22): case FR_REG (23):
	case FR_REG (24): case FR_REG (25): case FR_REG (26): case FR_REG (27):
	case FR_REG (28): case FR_REG (29): case FR_REG (30): case FR_REG (31):
	  fprintf (asm_out_file, "\t.save.gf 0x0, 0x%x\n",
		   1 << (src_regno - FR_REG (12)));
	  return 1;

	default:
	  return 0;
	}
    }

  return 0;
}


/* This function looks at a single insn and emits any directives
   required to unwind this insn.  */
void
process_for_unwind_directive (asm_out_file, insn)
     FILE *asm_out_file;
     rtx insn;
{
  if (flag_unwind_tables
      || (flag_exceptions && !USING_SJLJ_EXCEPTIONS))
    {
      rtx pat;

      if (GET_CODE (insn) == NOTE
	  && NOTE_LINE_NUMBER (insn) == NOTE_INSN_BASIC_BLOCK)
	{
	  block_num = NOTE_BASIC_BLOCK (insn)->index;

	  /* Restore unwind state from immediately before the epilogue.  */
	  if (need_copy_state)
	    {
	      fprintf (asm_out_file, "\t.body\n");
	      fprintf (asm_out_file, "\t.copy_state 1\n");
	      need_copy_state = 0;
	    }
	}

      if (! RTX_FRAME_RELATED_P (insn))
	return;

      pat = find_reg_note (insn, REG_FRAME_RELATED_EXPR, NULL_RTX);
      if (pat)
	pat = XEXP (pat, 0);
      else
	pat = PATTERN (insn);

      switch (GET_CODE (pat))
        {
	case SET:
	  process_set (asm_out_file, pat);
	  break;

	case PARALLEL:
	  {
	    int par_index;
	    int limit = XVECLEN (pat, 0);
	    for (par_index = 0; par_index < limit; par_index++)
	      {
		rtx x = XVECEXP (pat, 0, par_index);
		if (GET_CODE (x) == SET)
		  process_set (asm_out_file, x);
	      }
	    break;
	  }

	default:
	  abort ();
	}
    }
}


void
ia64_init_builtins ()
{
  tree psi_type_node = build_pointer_type (integer_type_node);
  tree pdi_type_node = build_pointer_type (long_integer_type_node);
  tree endlink = void_list_node;

  /* __sync_val_compare_and_swap_si, __sync_bool_compare_and_swap_si */
  tree si_ftype_psi_si_si
    = build_function_type (integer_type_node,
                           tree_cons (NULL_TREE, psi_type_node,
                                      tree_cons (NULL_TREE, integer_type_node,
                                                 tree_cons (NULL_TREE,
							    integer_type_node,
                                                            endlink))));

  /* __sync_val_compare_and_swap_di, __sync_bool_compare_and_swap_di */
  tree di_ftype_pdi_di_di
    = build_function_type (long_integer_type_node,
                           tree_cons (NULL_TREE, pdi_type_node,
                                      tree_cons (NULL_TREE,
						 long_integer_type_node,
                                                 tree_cons (NULL_TREE,
							long_integer_type_node,
							endlink))));
  /* __sync_synchronize */
  tree void_ftype_void
    = build_function_type (void_type_node, endlink);

  /* __sync_lock_test_and_set_si */
  tree si_ftype_psi_si
    = build_function_type (integer_type_node,
                           tree_cons (NULL_TREE, psi_type_node,
                           tree_cons (NULL_TREE, integer_type_node, endlink)));

  /* __sync_lock_test_and_set_di */
  tree di_ftype_pdi_di
    = build_function_type (long_integer_type_node,
                           tree_cons (NULL_TREE, pdi_type_node,
                           tree_cons (NULL_TREE, long_integer_type_node,
				      endlink)));

  /* __sync_lock_release_si */
  tree void_ftype_psi
    = build_function_type (void_type_node, tree_cons (NULL_TREE, psi_type_node,
						      endlink));

  /* __sync_lock_release_di */
  tree void_ftype_pdi
    = build_function_type (void_type_node, tree_cons (NULL_TREE, pdi_type_node,
						      endlink));

#define def_builtin(name, type, code) \
  builtin_function ((name), (type), (code), BUILT_IN_MD, NULL_PTR)

  def_builtin ("__sync_val_compare_and_swap_si", si_ftype_psi_si_si,
	       IA64_BUILTIN_VAL_COMPARE_AND_SWAP_SI);
  def_builtin ("__sync_val_compare_and_swap_di", di_ftype_pdi_di_di,
	       IA64_BUILTIN_VAL_COMPARE_AND_SWAP_DI);
  def_builtin ("__sync_bool_compare_and_swap_si", si_ftype_psi_si_si,
	       IA64_BUILTIN_BOOL_COMPARE_AND_SWAP_SI);
  def_builtin ("__sync_bool_compare_and_swap_di", di_ftype_pdi_di_di,
	       IA64_BUILTIN_BOOL_COMPARE_AND_SWAP_DI);

  def_builtin ("__sync_synchronize", void_ftype_void,
	       IA64_BUILTIN_SYNCHRONIZE);

  def_builtin ("__sync_lock_test_and_set_si", si_ftype_psi_si,
	       IA64_BUILTIN_LOCK_TEST_AND_SET_SI);
  def_builtin ("__sync_lock_test_and_set_di", di_ftype_pdi_di,
	       IA64_BUILTIN_LOCK_TEST_AND_SET_DI);
  def_builtin ("__sync_lock_release_si", void_ftype_psi,
	       IA64_BUILTIN_LOCK_RELEASE_SI);
  def_builtin ("__sync_lock_release_di", void_ftype_pdi,
	       IA64_BUILTIN_LOCK_RELEASE_DI);

  def_builtin ("__builtin_ia64_bsp",
	       build_function_type (ptr_type_node, endlink),
	       IA64_BUILTIN_BSP);

  def_builtin ("__builtin_ia64_flushrs", 
	       build_function_type (void_type_node, endlink), 
	       IA64_BUILTIN_FLUSHRS);

  def_builtin ("__sync_fetch_and_add_si", si_ftype_psi_si,
	       IA64_BUILTIN_FETCH_AND_ADD_SI);
  def_builtin ("__sync_fetch_and_sub_si", si_ftype_psi_si,
	       IA64_BUILTIN_FETCH_AND_SUB_SI);
  def_builtin ("__sync_fetch_and_or_si", si_ftype_psi_si,
	       IA64_BUILTIN_FETCH_AND_OR_SI);
  def_builtin ("__sync_fetch_and_and_si", si_ftype_psi_si,
	       IA64_BUILTIN_FETCH_AND_AND_SI);
  def_builtin ("__sync_fetch_and_xor_si", si_ftype_psi_si,
	       IA64_BUILTIN_FETCH_AND_XOR_SI);
  def_builtin ("__sync_fetch_and_nand_si", si_ftype_psi_si,
	       IA64_BUILTIN_FETCH_AND_NAND_SI);

  def_builtin ("__sync_add_and_fetch_si", si_ftype_psi_si,
	       IA64_BUILTIN_ADD_AND_FETCH_SI);
  def_builtin ("__sync_sub_and_fetch_si", si_ftype_psi_si,
	       IA64_BUILTIN_SUB_AND_FETCH_SI);
  def_builtin ("__sync_or_and_fetch_si", si_ftype_psi_si,
	       IA64_BUILTIN_OR_AND_FETCH_SI);
  def_builtin ("__sync_and_and_fetch_si", si_ftype_psi_si,
	       IA64_BUILTIN_AND_AND_FETCH_SI);
  def_builtin ("__sync_xor_and_fetch_si", si_ftype_psi_si,
	       IA64_BUILTIN_XOR_AND_FETCH_SI);
  def_builtin ("__sync_nand_and_fetch_si", si_ftype_psi_si,
	       IA64_BUILTIN_NAND_AND_FETCH_SI);

  def_builtin ("__sync_fetch_and_add_di", di_ftype_pdi_di,
	       IA64_BUILTIN_FETCH_AND_ADD_DI);
  def_builtin ("__sync_fetch_and_sub_di", di_ftype_pdi_di,
	       IA64_BUILTIN_FETCH_AND_SUB_DI);
  def_builtin ("__sync_fetch_and_or_di", di_ftype_pdi_di,
	       IA64_BUILTIN_FETCH_AND_OR_DI);
  def_builtin ("__sync_fetch_and_and_di", di_ftype_pdi_di,
	       IA64_BUILTIN_FETCH_AND_AND_DI);
  def_builtin ("__sync_fetch_and_xor_di", di_ftype_pdi_di,
	       IA64_BUILTIN_FETCH_AND_XOR_DI);
  def_builtin ("__sync_fetch_and_nand_di", di_ftype_pdi_di,
	       IA64_BUILTIN_FETCH_AND_NAND_DI);

  def_builtin ("__sync_add_and_fetch_di", di_ftype_pdi_di,
	       IA64_BUILTIN_ADD_AND_FETCH_DI);
  def_builtin ("__sync_sub_and_fetch_di", di_ftype_pdi_di,
	       IA64_BUILTIN_SUB_AND_FETCH_DI);
  def_builtin ("__sync_or_and_fetch_di", di_ftype_pdi_di,
	       IA64_BUILTIN_OR_AND_FETCH_DI);
  def_builtin ("__sync_and_and_fetch_di", di_ftype_pdi_di,
	       IA64_BUILTIN_AND_AND_FETCH_DI);
  def_builtin ("__sync_xor_and_fetch_di", di_ftype_pdi_di,
	       IA64_BUILTIN_XOR_AND_FETCH_DI);
  def_builtin ("__sync_nand_and_fetch_di", di_ftype_pdi_di,
	       IA64_BUILTIN_NAND_AND_FETCH_DI);

#undef def_builtin
}

/* Expand fetch_and_op intrinsics.  The basic code sequence is:

     mf
     tmp = [ptr];
     do {
       ret = tmp;
       ar.ccv = tmp;
       tmp <op>= value;
       cmpxchgsz.acq tmp = [ptr], tmp
     } while (tmp != ret)
*/

static rtx
ia64_expand_fetch_and_op (binoptab, mode, arglist, target)
     optab binoptab;
     enum machine_mode mode;
     tree arglist;
     rtx target;
{
  rtx ret, label, tmp, ccv, insn, mem, value;
  tree arg0, arg1;

  arg0 = TREE_VALUE (arglist);
  arg1 = TREE_VALUE (TREE_CHAIN (arglist));
  mem = expand_expr (arg0, NULL_RTX, Pmode, 0);
  value = expand_expr (arg1, NULL_RTX, mode, 0);

  mem = gen_rtx_MEM (mode, force_reg (Pmode, mem));
  MEM_VOLATILE_P (mem) = 1;

  if (target && register_operand (target, mode))
    ret = target;
  else
    ret = gen_reg_rtx (mode);

  emit_insn (gen_mf ());

  /* Special case for fetchadd instructions.  */
  if (binoptab == add_optab && fetchadd_operand (value, VOIDmode))
    {
      if (mode == SImode)
        insn = gen_fetchadd_acq_si (ret, mem, value);
      else
        insn = gen_fetchadd_acq_di (ret, mem, value);
      emit_insn (insn);
      return ret;
    }

  tmp = gen_reg_rtx (mode);
  ccv = gen_rtx_REG (mode, AR_CCV_REGNUM);
  emit_move_insn (tmp, mem);

  label = gen_label_rtx ();
  emit_label (label);
  emit_move_insn (ret, tmp);
  emit_move_insn (ccv, tmp);

  /* Perform the specific operation.  Special case NAND by noticing
     one_cmpl_optab instead.  */
  if (binoptab == one_cmpl_optab)
    {
      tmp = expand_unop (mode, binoptab, tmp, NULL, OPTAB_WIDEN);
      binoptab = and_optab;
    }
  tmp = expand_binop (mode, binoptab, tmp, value, tmp, 1, OPTAB_WIDEN);

  if (mode == SImode)
    insn = gen_cmpxchg_acq_si (tmp, mem, tmp, ccv);
  else
    insn = gen_cmpxchg_acq_di (tmp, mem, tmp, ccv);
  emit_insn (insn);

  emit_cmp_and_jump_insns (tmp, ret, NE, 0, mode, 1, 0, label);

  return ret;
}

/* Expand op_and_fetch intrinsics.  The basic code sequence is:

     mf
     tmp = [ptr];
     do {
       old = tmp;
       ar.ccv = tmp;
       ret = tmp + value;
       cmpxchgsz.acq tmp = [ptr], ret
     } while (tmp != old)
*/

static rtx
ia64_expand_op_and_fetch (binoptab, mode, arglist, target)
     optab binoptab;
     enum machine_mode mode;
     tree arglist;
     rtx target;
{
  rtx old, label, tmp, ret, ccv, insn, mem, value;
  tree arg0, arg1;

  arg0 = TREE_VALUE (arglist);
  arg1 = TREE_VALUE (TREE_CHAIN (arglist));
  mem = expand_expr (arg0, NULL_RTX, Pmode, 0);
  value = expand_expr (arg1, NULL_RTX, mode, 0);

  mem = gen_rtx_MEM (mode, force_reg (Pmode, mem));
  MEM_VOLATILE_P (mem) = 1;

  if (target && ! register_operand (target, mode))
    target = NULL_RTX;

  emit_insn (gen_mf ());
  tmp = gen_reg_rtx (mode);
  old = gen_reg_rtx (mode);
  ccv = gen_rtx_REG (mode, AR_CCV_REGNUM);

  emit_move_insn (tmp, mem);

  label = gen_label_rtx ();
  emit_label (label);
  emit_move_insn (old, tmp);
  emit_move_insn (ccv, tmp);

  /* Perform the specific operation.  Special case NAND by noticing
     one_cmpl_optab instead.  */
  if (binoptab == one_cmpl_optab)
    {
      tmp = expand_unop (mode, binoptab, tmp, NULL, OPTAB_WIDEN);
      binoptab = and_optab;
    }
  ret = expand_binop (mode, binoptab, tmp, value, target, 1, OPTAB_WIDEN);

  if (mode == SImode)
    insn = gen_cmpxchg_acq_si (tmp, mem, ret, ccv);
  else
    insn = gen_cmpxchg_acq_di (tmp, mem, ret, ccv);
  emit_insn (insn);

  emit_cmp_and_jump_insns (tmp, old, NE, 0, mode, 1, 0, label);

  return ret;
}

/* Expand val_ and bool_compare_and_swap.  For val_ we want:

     ar.ccv = oldval
     mf
     cmpxchgsz.acq ret = [ptr], newval, ar.ccv
     return ret

   For bool_ it's the same except return ret == oldval.
*/

static rtx
ia64_expand_compare_and_swap (mode, boolp, arglist, target)
     enum machine_mode mode;
     int boolp;
     tree arglist;
     rtx target;
{
  tree arg0, arg1, arg2;
  rtx mem, old, new, ccv, tmp, insn;

  arg0 = TREE_VALUE (arglist);
  arg1 = TREE_VALUE (TREE_CHAIN (arglist));
  arg2 = TREE_VALUE (TREE_CHAIN (TREE_CHAIN (arglist)));
  mem = expand_expr (arg0, NULL_RTX, Pmode, 0);
  old = expand_expr (arg1, NULL_RTX, mode, 0);
  new = expand_expr (arg2, NULL_RTX, mode, 0);

  mem = gen_rtx_MEM (mode, force_reg (Pmode, mem));
  MEM_VOLATILE_P (mem) = 1;

  if (! register_operand (old, mode))
    old = copy_to_mode_reg (mode, old);
  if (! register_operand (new, mode))
    new = copy_to_mode_reg (mode, new);

  if (! boolp && target && register_operand (target, mode))
    tmp = target;
  else
    tmp = gen_reg_rtx (mode);

  ccv = gen_rtx_REG (mode, AR_CCV_REGNUM);
  emit_move_insn (ccv, old);
  emit_insn (gen_mf ());
  if (mode == SImode)
    insn = gen_cmpxchg_acq_si (tmp, mem, new, ccv);
  else
    insn = gen_cmpxchg_acq_di (tmp, mem, new, ccv);
  emit_insn (insn);

  if (boolp)
    {
      if (! target)
	target = gen_reg_rtx (mode);
      return emit_store_flag_force (target, EQ, tmp, old, mode, 1, 1);
    }
  else
    return tmp;
}

/* Expand lock_test_and_set.  I.e. `xchgsz ret = [ptr], new'.  */

static rtx
ia64_expand_lock_test_and_set (mode, arglist, target)
     enum machine_mode mode;
     tree arglist;
     rtx target;
{
  tree arg0, arg1;
  rtx mem, new, ret, insn;

  arg0 = TREE_VALUE (arglist);
  arg1 = TREE_VALUE (TREE_CHAIN (arglist));
  mem = expand_expr (arg0, NULL_RTX, Pmode, 0);
  new = expand_expr (arg1, NULL_RTX, mode, 0);

  mem = gen_rtx_MEM (mode, force_reg (Pmode, mem));
  MEM_VOLATILE_P (mem) = 1;
  if (! register_operand (new, mode))
    new = copy_to_mode_reg (mode, new);

  if (target && register_operand (target, mode))
    ret = target;
  else
    ret = gen_reg_rtx (mode);

  if (mode == SImode)
    insn = gen_xchgsi (ret, mem, new);
  else
    insn = gen_xchgdi (ret, mem, new);
  emit_insn (insn);

  return ret;
}

/* Expand lock_release.  I.e. `stsz.rel [ptr] = r0'.  */

static rtx
ia64_expand_lock_release (mode, arglist, target)
     enum machine_mode mode;
     tree arglist;
     rtx target ATTRIBUTE_UNUSED;
{
  tree arg0;
  rtx mem;

  arg0 = TREE_VALUE (arglist);
  mem = expand_expr (arg0, NULL_RTX, Pmode, 0);

  mem = gen_rtx_MEM (mode, force_reg (Pmode, mem));
  MEM_VOLATILE_P (mem) = 1;

  emit_move_insn (mem, const0_rtx);

  return const0_rtx;
}

rtx
ia64_expand_builtin (exp, target, subtarget, mode, ignore)
     tree exp;
     rtx target;
     rtx subtarget ATTRIBUTE_UNUSED;
     enum machine_mode mode ATTRIBUTE_UNUSED;
     int ignore ATTRIBUTE_UNUSED;
{
  tree fndecl = TREE_OPERAND (TREE_OPERAND (exp, 0), 0);
  unsigned int fcode = DECL_FUNCTION_CODE (fndecl);
  tree arglist = TREE_OPERAND (exp, 1);

  switch (fcode)
    {
    case IA64_BUILTIN_BOOL_COMPARE_AND_SWAP_SI:
    case IA64_BUILTIN_VAL_COMPARE_AND_SWAP_SI:
    case IA64_BUILTIN_LOCK_TEST_AND_SET_SI:
    case IA64_BUILTIN_LOCK_RELEASE_SI:
    case IA64_BUILTIN_FETCH_AND_ADD_SI:
    case IA64_BUILTIN_FETCH_AND_SUB_SI:
    case IA64_BUILTIN_FETCH_AND_OR_SI:
    case IA64_BUILTIN_FETCH_AND_AND_SI:
    case IA64_BUILTIN_FETCH_AND_XOR_SI:
    case IA64_BUILTIN_FETCH_AND_NAND_SI:
    case IA64_BUILTIN_ADD_AND_FETCH_SI:
    case IA64_BUILTIN_SUB_AND_FETCH_SI:
    case IA64_BUILTIN_OR_AND_FETCH_SI:
    case IA64_BUILTIN_AND_AND_FETCH_SI:
    case IA64_BUILTIN_XOR_AND_FETCH_SI:
    case IA64_BUILTIN_NAND_AND_FETCH_SI:
      mode = SImode;
      break;

    case IA64_BUILTIN_BOOL_COMPARE_AND_SWAP_DI:
    case IA64_BUILTIN_VAL_COMPARE_AND_SWAP_DI:
    case IA64_BUILTIN_LOCK_TEST_AND_SET_DI:
    case IA64_BUILTIN_LOCK_RELEASE_DI:
    case IA64_BUILTIN_FETCH_AND_ADD_DI:
    case IA64_BUILTIN_FETCH_AND_SUB_DI:
    case IA64_BUILTIN_FETCH_AND_OR_DI:
    case IA64_BUILTIN_FETCH_AND_AND_DI:
    case IA64_BUILTIN_FETCH_AND_XOR_DI:
    case IA64_BUILTIN_FETCH_AND_NAND_DI:
    case IA64_BUILTIN_ADD_AND_FETCH_DI:
    case IA64_BUILTIN_SUB_AND_FETCH_DI:
    case IA64_BUILTIN_OR_AND_FETCH_DI:
    case IA64_BUILTIN_AND_AND_FETCH_DI:
    case IA64_BUILTIN_XOR_AND_FETCH_DI:
    case IA64_BUILTIN_NAND_AND_FETCH_DI:
      mode = DImode;
      break;

    default:
      break;
    }

  switch (fcode)
    {
    case IA64_BUILTIN_BOOL_COMPARE_AND_SWAP_SI:
    case IA64_BUILTIN_BOOL_COMPARE_AND_SWAP_DI:
      return ia64_expand_compare_and_swap (mode, 1, arglist, target);

    case IA64_BUILTIN_VAL_COMPARE_AND_SWAP_SI:
    case IA64_BUILTIN_VAL_COMPARE_AND_SWAP_DI:
      return ia64_expand_compare_and_swap (mode, 0, arglist, target);

    case IA64_BUILTIN_SYNCHRONIZE:
      emit_insn (gen_mf ());
      return const0_rtx;

    case IA64_BUILTIN_LOCK_TEST_AND_SET_SI:
    case IA64_BUILTIN_LOCK_TEST_AND_SET_DI:
      return ia64_expand_lock_test_and_set (mode, arglist, target);

    case IA64_BUILTIN_LOCK_RELEASE_SI:
    case IA64_BUILTIN_LOCK_RELEASE_DI:
      return ia64_expand_lock_release (mode, arglist, target);

    case IA64_BUILTIN_BSP:
      if (! target || ! register_operand (target, DImode))
	target = gen_reg_rtx (DImode);
      emit_insn (gen_bsp_value (target));
      return target;

    case IA64_BUILTIN_FLUSHRS:
      emit_insn (gen_flushrs ());
      return const0_rtx;

    case IA64_BUILTIN_FETCH_AND_ADD_SI:
    case IA64_BUILTIN_FETCH_AND_ADD_DI:
      return ia64_expand_fetch_and_op (add_optab, mode, arglist, target);

    case IA64_BUILTIN_FETCH_AND_SUB_SI:
    case IA64_BUILTIN_FETCH_AND_SUB_DI:
      return ia64_expand_fetch_and_op (sub_optab, mode, arglist, target);

    case IA64_BUILTIN_FETCH_AND_OR_SI:
    case IA64_BUILTIN_FETCH_AND_OR_DI:
      return ia64_expand_fetch_and_op (ior_optab, mode, arglist, target);

    case IA64_BUILTIN_FETCH_AND_AND_SI:
    case IA64_BUILTIN_FETCH_AND_AND_DI:
      return ia64_expand_fetch_and_op (and_optab, mode, arglist, target);

    case IA64_BUILTIN_FETCH_AND_XOR_SI:
    case IA64_BUILTIN_FETCH_AND_XOR_DI:
      return ia64_expand_fetch_and_op (xor_optab, mode, arglist, target);

    case IA64_BUILTIN_FETCH_AND_NAND_SI:
    case IA64_BUILTIN_FETCH_AND_NAND_DI:
      return ia64_expand_fetch_and_op (one_cmpl_optab, mode, arglist, target);

    case IA64_BUILTIN_ADD_AND_FETCH_SI:
    case IA64_BUILTIN_ADD_AND_FETCH_DI:
      return ia64_expand_op_and_fetch (add_optab, mode, arglist, target);

    case IA64_BUILTIN_SUB_AND_FETCH_SI:
    case IA64_BUILTIN_SUB_AND_FETCH_DI:
      return ia64_expand_op_and_fetch (sub_optab, mode, arglist, target);

    case IA64_BUILTIN_OR_AND_FETCH_SI:
    case IA64_BUILTIN_OR_AND_FETCH_DI:
      return ia64_expand_op_and_fetch (ior_optab, mode, arglist, target);

    case IA64_BUILTIN_AND_AND_FETCH_SI:
    case IA64_BUILTIN_AND_AND_FETCH_DI:
      return ia64_expand_op_and_fetch (and_optab, mode, arglist, target);

    case IA64_BUILTIN_XOR_AND_FETCH_SI:
    case IA64_BUILTIN_XOR_AND_FETCH_DI:
      return ia64_expand_op_and_fetch (xor_optab, mode, arglist, target);

    case IA64_BUILTIN_NAND_AND_FETCH_SI:
    case IA64_BUILTIN_NAND_AND_FETCH_DI:
      return ia64_expand_op_and_fetch (one_cmpl_optab, mode, arglist, target);

    default:
      break;
    }

  return NULL_RTX;
}
