/* Optimize by combining instructions for GNU compiler.
   Copyright (C) 1987-2018 Free Software Foundation, Inc.

This file is part of GCC.

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

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

You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING3.  If not see
<http://www.gnu.org/licenses/>.  */

/* This module is essentially the "combiner" phase of the U. of Arizona
   Portable Optimizer, but redone to work on our list-structured
   representation for RTL instead of their string representation.

   The LOG_LINKS of each insn identify the most recent assignment
   to each REG used in the insn.  It is a list of previous insns,
   each of which contains a SET for a REG that is used in this insn
   and not used or set in between.  LOG_LINKs never cross basic blocks.
   They were set up by the preceding pass (lifetime analysis).

   We try to combine each pair of insns joined by a logical link.
   We also try to combine triplets of insns A, B and C when C has
   a link back to B and B has a link back to A.  Likewise for a
   small number of quadruplets of insns A, B, C and D for which
   there's high likelihood of success.

   LOG_LINKS does not have links for use of the CC0.  They don't
   need to, because the insn that sets the CC0 is always immediately
   before the insn that tests it.  So we always regard a branch
   insn as having a logical link to the preceding insn.  The same is true
   for an insn explicitly using CC0.

   We check (with modified_between_p) to avoid combining in such a way
   as to move a computation to a place where its value would be different.

   Combination is done by mathematically substituting the previous
   insn(s) values for the regs they set into the expressions in
   the later insns that refer to these regs.  If the result is a valid insn
   for our target machine, according to the machine description,
   we install it, delete the earlier insns, and update the data flow
   information (LOG_LINKS and REG_NOTES) for what we did.

   There are a few exceptions where the dataflow information isn't
   completely updated (however this is only a local issue since it is
   regenerated before the next pass that uses it):

   - reg_live_length is not updated
   - reg_n_refs is not adjusted in the rare case when a register is
     no longer required in a computation
   - there are extremely rare cases (see distribute_notes) when a
     REG_DEAD note is lost
   - a LOG_LINKS entry that refers to an insn with multiple SETs may be
     removed because there is no way to know which register it was
     linking

   To simplify substitution, we combine only when the earlier insn(s)
   consist of only a single assignment.  To simplify updating afterward,
   we never combine when a subroutine call appears in the middle.

   Since we do not represent assignments to CC0 explicitly except when that
   is all an insn does, there is no LOG_LINKS entry in an insn that uses
   the condition code for the insn that set the condition code.
   Fortunately, these two insns must be consecutive.
   Therefore, every JUMP_INSN is taken to have an implicit logical link
   to the preceding insn.  This is not quite right, since non-jumps can
   also use the condition code; but in practice such insns would not
   combine anyway.  */

#include "config.h"
#include "system.h"
#include "coretypes.h"
#include "backend.h"
#include "target.h"
#include "rtl.h"
#include "tree.h"
#include "cfghooks.h"
#include "predict.h"
#include "df.h"
#include "memmodel.h"
#include "tm_p.h"
#include "optabs.h"
#include "regs.h"
#include "emit-rtl.h"
#include "recog.h"
#include "cgraph.h"
#include "stor-layout.h"
#include "cfgrtl.h"
#include "cfgcleanup.h"
/* Include expr.h after insn-config.h so we get HAVE_conditional_move.  */
#include "explow.h"
#include "insn-attr.h"
#include "rtlhooks-def.h"
#include "expr.h"
#include "params.h"
#include "tree-pass.h"
#include "valtrack.h"
#include "rtl-iter.h"
#include "print-rtl.h"

/* Number of attempts to combine instructions in this function.  */

static int combine_attempts;

/* Number of attempts that got as far as substitution in this function.  */

static int combine_merges;

/* Number of instructions combined with added SETs in this function.  */

static int combine_extras;

/* Number of instructions combined in this function.  */

static int combine_successes;

/* Totals over entire compilation.  */

static int total_attempts, total_merges, total_extras, total_successes;

/* combine_instructions may try to replace the right hand side of the
   second instruction with the value of an associated REG_EQUAL note
   before throwing it at try_combine.  That is problematic when there
   is a REG_DEAD note for a register used in the old right hand side
   and can cause distribute_notes to do wrong things.  This is the
   second instruction if it has been so modified, null otherwise.  */

static rtx_insn *i2mod;

/* When I2MOD is nonnull, this is a copy of the old right hand side.  */

static rtx i2mod_old_rhs;

/* When I2MOD is nonnull, this is a copy of the new right hand side.  */

static rtx i2mod_new_rhs;

struct reg_stat_type {
  /* Record last point of death of (hard or pseudo) register n.  */
  rtx_insn			*last_death;

  /* Record last point of modification of (hard or pseudo) register n.  */
  rtx_insn			*last_set;

  /* The next group of fields allows the recording of the last value assigned
     to (hard or pseudo) register n.  We use this information to see if an
     operation being processed is redundant given a prior operation performed
     on the register.  For example, an `and' with a constant is redundant if
     all the zero bits are already known to be turned off.

     We use an approach similar to that used by cse, but change it in the
     following ways:

     (1) We do not want to reinitialize at each label.
     (2) It is useful, but not critical, to know the actual value assigned
	 to a register.  Often just its form is helpful.

     Therefore, we maintain the following fields:

     last_set_value		the last value assigned
     last_set_label		records the value of label_tick when the
				register was assigned
     last_set_table_tick	records the value of label_tick when a
				value using the register is assigned
     last_set_invalid		set to nonzero when it is not valid
				to use the value of this register in some
				register's value

     To understand the usage of these tables, it is important to understand
     the distinction between the value in last_set_value being valid and
     the register being validly contained in some other expression in the
     table.

     (The next two parameters are out of date).

     reg_stat[i].last_set_value is valid if it is nonzero, and either
     reg_n_sets[i] is 1 or reg_stat[i].last_set_label == label_tick.

     Register I may validly appear in any expression returned for the value
     of another register if reg_n_sets[i] is 1.  It may also appear in the
     value for register J if reg_stat[j].last_set_invalid is zero, or
     reg_stat[i].last_set_label < reg_stat[j].last_set_label.

     If an expression is found in the table containing a register which may
     not validly appear in an expression, the register is replaced by
     something that won't match, (clobber (const_int 0)).  */

  /* Record last value assigned to (hard or pseudo) register n.  */

  rtx				last_set_value;

  /* Record the value of label_tick when an expression involving register n
     is placed in last_set_value.  */

  int				last_set_table_tick;

  /* Record the value of label_tick when the value for register n is placed in
     last_set_value.  */

  int				last_set_label;

  /* These fields are maintained in parallel with last_set_value and are
     used to store the mode in which the register was last set, the bits
     that were known to be zero when it was last set, and the number of
     sign bits copies it was known to have when it was last set.  */

  unsigned HOST_WIDE_INT	last_set_nonzero_bits;
  char				last_set_sign_bit_copies;
  ENUM_BITFIELD(machine_mode)	last_set_mode : 8;

  /* Set nonzero if references to register n in expressions should not be
     used.  last_set_invalid is set nonzero when this register is being
     assigned to and last_set_table_tick == label_tick.  */

  char				last_set_invalid;

  /* Some registers that are set more than once and used in more than one
     basic block are nevertheless always set in similar ways.  For example,
     a QImode register may be loaded from memory in two places on a machine
     where byte loads zero extend.

     We record in the following fields if a register has some leading bits
     that are always equal to the sign bit, and what we know about the
     nonzero bits of a register, specifically which bits are known to be
     zero.

     If an entry is zero, it means that we don't know anything special.  */

  unsigned char			sign_bit_copies;

  unsigned HOST_WIDE_INT	nonzero_bits;

  /* Record the value of the label_tick when the last truncation
     happened.  The field truncated_to_mode is only valid if
     truncation_label == label_tick.  */

  int				truncation_label;

  /* Record the last truncation seen for this register.  If truncation
     is not a nop to this mode we might be able to save an explicit
     truncation if we know that value already contains a truncated
     value.  */

  ENUM_BITFIELD(machine_mode)	truncated_to_mode : 8;
};


static vec<reg_stat_type> reg_stat;

/* One plus the highest pseudo for which we track REG_N_SETS.
   regstat_init_n_sets_and_refs allocates the array for REG_N_SETS just once,
   but during combine_split_insns new pseudos can be created.  As we don't have
   updated DF information in that case, it is hard to initialize the array
   after growing.  The combiner only cares about REG_N_SETS (regno) == 1,
   so instead of growing the arrays, just assume all newly created pseudos
   during combine might be set multiple times.  */

static unsigned int reg_n_sets_max;

/* Record the luid of the last insn that invalidated memory
   (anything that writes memory, and subroutine calls, but not pushes).  */

static int mem_last_set;

/* Record the luid of the last CALL_INSN
   so we can tell whether a potential combination crosses any calls.  */

static int last_call_luid;

/* When `subst' is called, this is the insn that is being modified
   (by combining in a previous insn).  The PATTERN of this insn
   is still the old pattern partially modified and it should not be
   looked at, but this may be used to examine the successors of the insn
   to judge whether a simplification is valid.  */

static rtx_insn *subst_insn;

/* This is the lowest LUID that `subst' is currently dealing with.
   get_last_value will not return a value if the register was set at or
   after this LUID.  If not for this mechanism, we could get confused if
   I2 or I1 in try_combine were an insn that used the old value of a register
   to obtain a new value.  In that case, we might erroneously get the
   new value of the register when we wanted the old one.  */

static int subst_low_luid;

/* This contains any hard registers that are used in newpat; reg_dead_at_p
   must consider all these registers to be always live.  */

static HARD_REG_SET newpat_used_regs;

/* This is an insn to which a LOG_LINKS entry has been added.  If this
   insn is the earlier than I2 or I3, combine should rescan starting at
   that location.  */

static rtx_insn *added_links_insn;

/* And similarly, for notes.  */

static rtx_insn *added_notes_insn;

/* Basic block in which we are performing combines.  */
static basic_block this_basic_block;
static bool optimize_this_for_speed_p;


/* Length of the currently allocated uid_insn_cost array.  */

static int max_uid_known;

/* The following array records the insn_cost for every insn
   in the instruction stream.  */

static int *uid_insn_cost;

/* The following array records the LOG_LINKS for every insn in the
   instruction stream as struct insn_link pointers.  */

struct insn_link {
  rtx_insn *insn;
  unsigned int regno;
  struct insn_link *next;
};

static struct insn_link **uid_log_links;

static inline int
insn_uid_check (const_rtx insn)
{
  int uid = INSN_UID (insn);
  gcc_checking_assert (uid <= max_uid_known);
  return uid;
}

#define INSN_COST(INSN)		(uid_insn_cost[insn_uid_check (INSN)])
#define LOG_LINKS(INSN)		(uid_log_links[insn_uid_check (INSN)])

#define FOR_EACH_LOG_LINK(L, INSN)				\
  for ((L) = LOG_LINKS (INSN); (L); (L) = (L)->next)

/* Links for LOG_LINKS are allocated from this obstack.  */

static struct obstack insn_link_obstack;

/* Allocate a link.  */

static inline struct insn_link *
alloc_insn_link (rtx_insn *insn, unsigned int regno, struct insn_link *next)
{
  struct insn_link *l
    = (struct insn_link *) obstack_alloc (&insn_link_obstack,
					  sizeof (struct insn_link));
  l->insn = insn;
  l->regno = regno;
  l->next = next;
  return l;
}

/* Incremented for each basic block.  */

static int label_tick;

/* Reset to label_tick for each extended basic block in scanning order.  */

static int label_tick_ebb_start;

/* Mode used to compute significance in reg_stat[].nonzero_bits.  It is the
   largest integer mode that can fit in HOST_BITS_PER_WIDE_INT.  */

static scalar_int_mode nonzero_bits_mode;

/* Nonzero when reg_stat[].nonzero_bits and reg_stat[].sign_bit_copies can
   be safely used.  It is zero while computing them and after combine has
   completed.  This former test prevents propagating values based on
   previously set values, which can be incorrect if a variable is modified
   in a loop.  */

static int nonzero_sign_valid;


/* Record one modification to rtl structure
   to be undone by storing old_contents into *where.  */

enum undo_kind { UNDO_RTX, UNDO_INT, UNDO_MODE, UNDO_LINKS };

struct undo
{
  struct undo *next;
  enum undo_kind kind;
  union { rtx r; int i; machine_mode m; struct insn_link *l; } old_contents;
  union { rtx *r; int *i; struct insn_link **l; } where;
};

/* Record a bunch of changes to be undone, up to MAX_UNDO of them.
   num_undo says how many are currently recorded.

   other_insn is nonzero if we have modified some other insn in the process
   of working on subst_insn.  It must be verified too.  */

struct undobuf
{
  struct undo *undos;
  struct undo *frees;
  rtx_insn *other_insn;
};

static struct undobuf undobuf;

/* Number of times the pseudo being substituted for
   was found and replaced.  */

static int n_occurrences;

static rtx reg_nonzero_bits_for_combine (const_rtx, scalar_int_mode,
					 scalar_int_mode,
					 unsigned HOST_WIDE_INT *);
static rtx reg_num_sign_bit_copies_for_combine (const_rtx, scalar_int_mode,
						scalar_int_mode,
						unsigned int *);
static void do_SUBST (rtx *, rtx);
static void do_SUBST_INT (int *, int);
static void init_reg_last (void);
static void setup_incoming_promotions (rtx_insn *);
static void set_nonzero_bits_and_sign_copies (rtx, const_rtx, void *);
static int cant_combine_insn_p (rtx_insn *);
static int can_combine_p (rtx_insn *, rtx_insn *, rtx_insn *, rtx_insn *,
			  rtx_insn *, rtx_insn *, rtx *, rtx *);
static int combinable_i3pat (rtx_insn *, rtx *, rtx, rtx, rtx, int, int, rtx *);
static int contains_muldiv (rtx);
static rtx_insn *try_combine (rtx_insn *, rtx_insn *, rtx_insn *, rtx_insn *,
			      int *, rtx_insn *);
static void undo_all (void);
static void undo_commit (void);
static rtx *find_split_point (rtx *, rtx_insn *, bool);
static rtx subst (rtx, rtx, rtx, int, int, int);
static rtx combine_simplify_rtx (rtx, machine_mode, int, int);
static rtx simplify_if_then_else (rtx);
static rtx simplify_set (rtx);
static rtx simplify_logical (rtx);
static rtx expand_compound_operation (rtx);
static const_rtx expand_field_assignment (const_rtx);
static rtx make_extraction (machine_mode, rtx, HOST_WIDE_INT,
			    rtx, unsigned HOST_WIDE_INT, int, int, int);
static int get_pos_from_mask (unsigned HOST_WIDE_INT,
			      unsigned HOST_WIDE_INT *);
static rtx canon_reg_for_combine (rtx, rtx);
static rtx force_int_to_mode (rtx, scalar_int_mode, scalar_int_mode,
			      scalar_int_mode, unsigned HOST_WIDE_INT, int);
static rtx force_to_mode (rtx, machine_mode,
			  unsigned HOST_WIDE_INT, int);
static rtx if_then_else_cond (rtx, rtx *, rtx *);
static rtx known_cond (rtx, enum rtx_code, rtx, rtx);
static int rtx_equal_for_field_assignment_p (rtx, rtx, bool = false);
static rtx make_field_assignment (rtx);
static rtx apply_distributive_law (rtx);
static rtx distribute_and_simplify_rtx (rtx, int);
static rtx simplify_and_const_int_1 (scalar_int_mode, rtx,
				     unsigned HOST_WIDE_INT);
static rtx simplify_and_const_int (rtx, scalar_int_mode, rtx,
				   unsigned HOST_WIDE_INT);
static int merge_outer_ops (enum rtx_code *, HOST_WIDE_INT *, enum rtx_code,
			    HOST_WIDE_INT, machine_mode, int *);
static rtx simplify_shift_const_1 (enum rtx_code, machine_mode, rtx, int);
static rtx simplify_shift_const (rtx, enum rtx_code, machine_mode, rtx,
				 int);
static int recog_for_combine (rtx *, rtx_insn *, rtx *);
static rtx gen_lowpart_for_combine (machine_mode, rtx);
static enum rtx_code simplify_compare_const (enum rtx_code, machine_mode,
					     rtx, rtx *);
static enum rtx_code simplify_comparison (enum rtx_code, rtx *, rtx *);
static void update_table_tick (rtx);
static void record_value_for_reg (rtx, rtx_insn *, rtx);
static void check_promoted_subreg (rtx_insn *, rtx);
static void record_dead_and_set_regs_1 (rtx, const_rtx, void *);
static void record_dead_and_set_regs (rtx_insn *);
static int get_last_value_validate (rtx *, rtx_insn *, int, int);
static rtx get_last_value (const_rtx);
static void reg_dead_at_p_1 (rtx, const_rtx, void *);
static int reg_dead_at_p (rtx, rtx_insn *);
static void move_deaths (rtx, rtx, int, rtx_insn *, rtx *);
static int reg_bitfield_target_p (rtx, rtx);
static void distribute_notes (rtx, rtx_insn *, rtx_insn *, rtx_insn *, rtx, rtx, rtx);
static void distribute_links (struct insn_link *);
static void mark_used_regs_combine (rtx);
static void record_promoted_value (rtx_insn *, rtx);
static bool unmentioned_reg_p (rtx, rtx);
static void record_truncated_values (rtx *, void *);
static bool reg_truncated_to_mode (machine_mode, const_rtx);
static rtx gen_lowpart_or_truncate (machine_mode, rtx);


/* It is not safe to use ordinary gen_lowpart in combine.
   See comments in gen_lowpart_for_combine.  */
#undef RTL_HOOKS_GEN_LOWPART
#define RTL_HOOKS_GEN_LOWPART              gen_lowpart_for_combine

/* Our implementation of gen_lowpart never emits a new pseudo.  */
#undef RTL_HOOKS_GEN_LOWPART_NO_EMIT
#define RTL_HOOKS_GEN_LOWPART_NO_EMIT      gen_lowpart_for_combine

#undef RTL_HOOKS_REG_NONZERO_REG_BITS
#define RTL_HOOKS_REG_NONZERO_REG_BITS     reg_nonzero_bits_for_combine

#undef RTL_HOOKS_REG_NUM_SIGN_BIT_COPIES
#define RTL_HOOKS_REG_NUM_SIGN_BIT_COPIES  reg_num_sign_bit_copies_for_combine

#undef RTL_HOOKS_REG_TRUNCATED_TO_MODE
#define RTL_HOOKS_REG_TRUNCATED_TO_MODE    reg_truncated_to_mode

static const struct rtl_hooks combine_rtl_hooks = RTL_HOOKS_INITIALIZER;


/* Convenience wrapper for the canonicalize_comparison target hook.
   Target hooks cannot use enum rtx_code.  */
static inline void
target_canonicalize_comparison (enum rtx_code *code, rtx *op0, rtx *op1,
				bool op0_preserve_value)
{
  int code_int = (int)*code;
  targetm.canonicalize_comparison (&code_int, op0, op1, op0_preserve_value);
  *code = (enum rtx_code)code_int;
}

/* Try to split PATTERN found in INSN.  This returns NULL_RTX if
   PATTERN can not be split.  Otherwise, it returns an insn sequence.
   This is a wrapper around split_insns which ensures that the
   reg_stat vector is made larger if the splitter creates a new
   register.  */

static rtx_insn *
combine_split_insns (rtx pattern, rtx_insn *insn)
{
  rtx_insn *ret;
  unsigned int nregs;

  ret = split_insns (pattern, insn);
  nregs = max_reg_num ();
  if (nregs > reg_stat.length ())
    reg_stat.safe_grow_cleared (nregs);
  return ret;
}

/* This is used by find_single_use to locate an rtx in LOC that
   contains exactly one use of DEST, which is typically either a REG
   or CC0.  It returns a pointer to the innermost rtx expression
   containing DEST.  Appearances of DEST that are being used to
   totally replace it are not counted.  */

static rtx *
find_single_use_1 (rtx dest, rtx *loc)
{
  rtx x = *loc;
  enum rtx_code code = GET_CODE (x);
  rtx *result = NULL;
  rtx *this_result;
  int i;
  const char *fmt;

  switch (code)
    {
    case CONST:
    case LABEL_REF:
    case SYMBOL_REF:
    CASE_CONST_ANY:
    case CLOBBER:
    case CLOBBER_HIGH:
      return 0;

    case SET:
      /* If the destination is anything other than CC0, PC, a REG or a SUBREG
	 of a REG that occupies all of the REG, the insn uses DEST if
	 it is mentioned in the destination or the source.  Otherwise, we
	 need just check the source.  */
      if (GET_CODE (SET_DEST (x)) != CC0
	  && GET_CODE (SET_DEST (x)) != PC
	  && !REG_P (SET_DEST (x))
	  && ! (GET_CODE (SET_DEST (x)) == SUBREG
		&& REG_P (SUBREG_REG (SET_DEST (x)))
		&& !read_modify_subreg_p (SET_DEST (x))))
	break;

      return find_single_use_1 (dest, &SET_SRC (x));

    case MEM:
    case SUBREG:
      return find_single_use_1 (dest, &XEXP (x, 0));

    default:
      break;
    }

  /* If it wasn't one of the common cases above, check each expression and
     vector of this code.  Look for a unique usage of DEST.  */

  fmt = GET_RTX_FORMAT (code);
  for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
    {
      if (fmt[i] == 'e')
	{
	  if (dest == XEXP (x, i)
	      || (REG_P (dest) && REG_P (XEXP (x, i))
		  && REGNO (dest) == REGNO (XEXP (x, i))))
	    this_result = loc;
	  else
	    this_result = find_single_use_1 (dest, &XEXP (x, i));

	  if (result == NULL)
	    result = this_result;
	  else if (this_result)
	    /* Duplicate usage.  */
	    return NULL;
	}
      else if (fmt[i] == 'E')
	{
	  int j;

	  for (j = XVECLEN (x, i) - 1; j >= 0; j--)
	    {
	      if (XVECEXP (x, i, j) == dest
		  || (REG_P (dest)
		      && REG_P (XVECEXP (x, i, j))
		      && REGNO (XVECEXP (x, i, j)) == REGNO (dest)))
		this_result = loc;
	      else
		this_result = find_single_use_1 (dest, &XVECEXP (x, i, j));

	      if (result == NULL)
		result = this_result;
	      else if (this_result)
		return NULL;
	    }
	}
    }

  return result;
}


/* See if DEST, produced in INSN, is used only a single time in the
   sequel.  If so, return a pointer to the innermost rtx expression in which
   it is used.

   If PLOC is nonzero, *PLOC is set to the insn containing the single use.

   If DEST is cc0_rtx, we look only at the next insn.  In that case, we don't
   care about REG_DEAD notes or LOG_LINKS.

   Otherwise, we find the single use by finding an insn that has a
   LOG_LINKS pointing at INSN and has a REG_DEAD note for DEST.  If DEST is
   only referenced once in that insn, we know that it must be the first
   and last insn referencing DEST.  */

static rtx *
find_single_use (rtx dest, rtx_insn *insn, rtx_insn **ploc)
{
  basic_block bb;
  rtx_insn *next;
  rtx *result;
  struct insn_link *link;

  if (dest == cc0_rtx)
    {
      next = NEXT_INSN (insn);
      if (next == 0
	  || (!NONJUMP_INSN_P (next) && !JUMP_P (next)))
	return 0;

      result = find_single_use_1 (dest, &PATTERN (next));
      if (result && ploc)
	*ploc = next;
      return result;
    }

  if (!REG_P (dest))
    return 0;

  bb = BLOCK_FOR_INSN (insn);
  for (next = NEXT_INSN (insn);
       next && BLOCK_FOR_INSN (next) == bb;
       next = NEXT_INSN (next))
    if (NONDEBUG_INSN_P (next) && dead_or_set_p (next, dest))
      {
	FOR_EACH_LOG_LINK (link, next)
	  if (link->insn == insn && link->regno == REGNO (dest))
	    break;

	if (link)
	  {
	    result = find_single_use_1 (dest, &PATTERN (next));
	    if (ploc)
	      *ploc = next;
	    return result;
	  }
      }

  return 0;
}

/* Substitute NEWVAL, an rtx expression, into INTO, a place in some
   insn.  The substitution can be undone by undo_all.  If INTO is already
   set to NEWVAL, do not record this change.  Because computing NEWVAL might
   also call SUBST, we have to compute it before we put anything into
   the undo table.  */

static void
do_SUBST (rtx *into, rtx newval)
{
  struct undo *buf;
  rtx oldval = *into;

  if (oldval == newval)
    return;

  /* We'd like to catch as many invalid transformations here as
     possible.  Unfortunately, there are way too many mode changes
     that are perfectly valid, so we'd waste too much effort for
     little gain doing the checks here.  Focus on catching invalid
     transformations involving integer constants.  */
  if (GET_MODE_CLASS (GET_MODE (oldval)) == MODE_INT
      && CONST_INT_P (newval))
    {
      /* Sanity check that we're replacing oldval with a CONST_INT
	 that is a valid sign-extension for the original mode.  */
      gcc_assert (INTVAL (newval)
		  == trunc_int_for_mode (INTVAL (newval), GET_MODE (oldval)));

      /* Replacing the operand of a SUBREG or a ZERO_EXTEND with a
	 CONST_INT is not valid, because after the replacement, the
	 original mode would be gone.  Unfortunately, we can't tell
	 when do_SUBST is called to replace the operand thereof, so we
	 perform this test on oldval instead, checking whether an
	 invalid replacement took place before we got here.  */
      gcc_assert (!(GET_CODE (oldval) == SUBREG
		    && CONST_INT_P (SUBREG_REG (oldval))));
      gcc_assert (!(GET_CODE (oldval) == ZERO_EXTEND
		    && CONST_INT_P (XEXP (oldval, 0))));
    }

  if (undobuf.frees)
    buf = undobuf.frees, undobuf.frees = buf->next;
  else
    buf = XNEW (struct undo);

  buf->kind = UNDO_RTX;
  buf->where.r = into;
  buf->old_contents.r = oldval;
  *into = newval;

  buf->next = undobuf.undos, undobuf.undos = buf;
}

#define SUBST(INTO, NEWVAL)	do_SUBST (&(INTO), (NEWVAL))

/* Similar to SUBST, but NEWVAL is an int expression.  Note that substitution
   for the value of a HOST_WIDE_INT value (including CONST_INT) is
   not safe.  */

static void
do_SUBST_INT (int *into, int newval)
{
  struct undo *buf;
  int oldval = *into;

  if (oldval == newval)
    return;

  if (undobuf.frees)
    buf = undobuf.frees, undobuf.frees = buf->next;
  else
    buf = XNEW (struct undo);

  buf->kind = UNDO_INT;
  buf->where.i = into;
  buf->old_contents.i = oldval;
  *into = newval;

  buf->next = undobuf.undos, undobuf.undos = buf;
}

#define SUBST_INT(INTO, NEWVAL)  do_SUBST_INT (&(INTO), (NEWVAL))

/* Similar to SUBST, but just substitute the mode.  This is used when
   changing the mode of a pseudo-register, so that any other
   references to the entry in the regno_reg_rtx array will change as
   well.  */

static void
do_SUBST_MODE (rtx *into, machine_mode newval)
{
  struct undo *buf;
  machine_mode oldval = GET_MODE (*into);

  if (oldval == newval)
    return;

  if (undobuf.frees)
    buf = undobuf.frees, undobuf.frees = buf->next;
  else
    buf = XNEW (struct undo);

  buf->kind = UNDO_MODE;
  buf->where.r = into;
  buf->old_contents.m = oldval;
  adjust_reg_mode (*into, newval);

  buf->next = undobuf.undos, undobuf.undos = buf;
}

#define SUBST_MODE(INTO, NEWVAL)  do_SUBST_MODE (&(INTO), (NEWVAL))

/* Similar to SUBST, but NEWVAL is a LOG_LINKS expression.  */

static void
do_SUBST_LINK (struct insn_link **into, struct insn_link *newval)
{
  struct undo *buf;
  struct insn_link * oldval = *into;

  if (oldval == newval)
    return;

  if (undobuf.frees)
    buf = undobuf.frees, undobuf.frees = buf->next;
  else
    buf = XNEW (struct undo);

  buf->kind = UNDO_LINKS;
  buf->where.l = into;
  buf->old_contents.l = oldval;
  *into = newval;

  buf->next = undobuf.undos, undobuf.undos = buf;
}

#define SUBST_LINK(oldval, newval) do_SUBST_LINK (&oldval, newval)

/* Subroutine of try_combine.  Determine whether the replacement patterns
   NEWPAT, NEWI2PAT and NEWOTHERPAT are cheaper according to insn_cost
   than the original sequence I0, I1, I2, I3 and undobuf.other_insn.  Note
   that I0, I1 and/or NEWI2PAT may be NULL_RTX.  Similarly, NEWOTHERPAT and
   undobuf.other_insn may also both be NULL_RTX.  Return false if the cost
   of all the instructions can be estimated and the replacements are more
   expensive than the original sequence.  */

static bool
combine_validate_cost (rtx_insn *i0, rtx_insn *i1, rtx_insn *i2, rtx_insn *i3,
		       rtx newpat, rtx newi2pat, rtx newotherpat)
{
  int i0_cost, i1_cost, i2_cost, i3_cost;
  int new_i2_cost, new_i3_cost;
  int old_cost, new_cost;

  /* Lookup the original insn_costs.  */
  i2_cost = INSN_COST (i2);
  i3_cost = INSN_COST (i3);

  if (i1)
    {
      i1_cost = INSN_COST (i1);
      if (i0)
	{
	  i0_cost = INSN_COST (i0);
	  old_cost = (i0_cost > 0 && i1_cost > 0 && i2_cost > 0 && i3_cost > 0
		      ? i0_cost + i1_cost + i2_cost + i3_cost : 0);
	}
      else
	{
	  old_cost = (i1_cost > 0 && i2_cost > 0 && i3_cost > 0
		      ? i1_cost + i2_cost + i3_cost : 0);
	  i0_cost = 0;
	}
    }
  else
    {
      old_cost = (i2_cost > 0 && i3_cost > 0) ? i2_cost + i3_cost : 0;
      i1_cost = i0_cost = 0;
    }

  /* If we have split a PARALLEL I2 to I1,I2, we have counted its cost twice;
     correct that.  */
  if (old_cost && i1 && INSN_UID (i1) == INSN_UID (i2))
    old_cost -= i1_cost;


  /* Calculate the replacement insn_costs.  */
  rtx tmp = PATTERN (i3);
  PATTERN (i3) = newpat;
  int tmpi = INSN_CODE (i3);
  INSN_CODE (i3) = -1;
  new_i3_cost = insn_cost (i3, optimize_this_for_speed_p);
  PATTERN (i3) = tmp;
  INSN_CODE (i3) = tmpi;
  if (newi2pat)
    {
      tmp = PATTERN (i2);
      PATTERN (i2) = newi2pat;
      tmpi = INSN_CODE (i2);
      INSN_CODE (i2) = -1;
      new_i2_cost = insn_cost (i2, optimize_this_for_speed_p);
      PATTERN (i2) = tmp;
      INSN_CODE (i2) = tmpi;
      new_cost = (new_i2_cost > 0 && new_i3_cost > 0)
		 ? new_i2_cost + new_i3_cost : 0;
    }
  else
    {
      new_cost = new_i3_cost;
      new_i2_cost = 0;
    }

  if (undobuf.other_insn)
    {
      int old_other_cost, new_other_cost;

      old_other_cost = INSN_COST (undobuf.other_insn);
      tmp = PATTERN (undobuf.other_insn);
      PATTERN (undobuf.other_insn) = newotherpat;
      tmpi = INSN_CODE (undobuf.other_insn);
      INSN_CODE (undobuf.other_insn) = -1;
      new_other_cost = insn_cost (undobuf.other_insn,
				  optimize_this_for_speed_p);
      PATTERN (undobuf.other_insn) = tmp;
      INSN_CODE (undobuf.other_insn) = tmpi;
      if (old_other_cost > 0 && new_other_cost > 0)
	{
	  old_cost += old_other_cost;
	  new_cost += new_other_cost;
	}
      else
	old_cost = 0;
    }

  /* Disallow this combination if both new_cost and old_cost are greater than
     zero, and new_cost is greater than old cost.  */
  int reject = old_cost > 0 && new_cost > old_cost;

  if (dump_file)
    {
      fprintf (dump_file, "%s combination of insns ",
	       reject ? "rejecting" : "allowing");
      if (i0)
	fprintf (dump_file, "%d, ", INSN_UID (i0));
      if (i1 && INSN_UID (i1) != INSN_UID (i2))
	fprintf (dump_file, "%d, ", INSN_UID (i1));
      fprintf (dump_file, "%d and %d\n", INSN_UID (i2), INSN_UID (i3));

      fprintf (dump_file, "original costs ");
      if (i0)
	fprintf (dump_file, "%d + ", i0_cost);
      if (i1 && INSN_UID (i1) != INSN_UID (i2))
	fprintf (dump_file, "%d + ", i1_cost);
      fprintf (dump_file, "%d + %d = %d\n", i2_cost, i3_cost, old_cost);

      if (newi2pat)
	fprintf (dump_file, "replacement costs %d + %d = %d\n",
		 new_i2_cost, new_i3_cost, new_cost);
      else
	fprintf (dump_file, "replacement cost %d\n", new_cost);
    }

  if (reject)
    return false;

  /* Update the uid_insn_cost array with the replacement costs.  */
  INSN_COST (i2) = new_i2_cost;
  INSN_COST (i3) = new_i3_cost;
  if (i1)
    {
      INSN_COST (i1) = 0;
      if (i0)
	INSN_COST (i0) = 0;
    }

  return true;
}


/* Delete any insns that copy a register to itself.  */

static void
delete_noop_moves (void)
{
  rtx_insn *insn, *next;
  basic_block bb;

  FOR_EACH_BB_FN (bb, cfun)
    {
      for (insn = BB_HEAD (bb); insn != NEXT_INSN (BB_END (bb)); insn = next)
	{
	  next = NEXT_INSN (insn);
	  if (INSN_P (insn) && noop_move_p (insn))
	    {
	      if (dump_file)
		fprintf (dump_file, "deleting noop move %d\n", INSN_UID (insn));

	      delete_insn_and_edges (insn);
	    }
	}
    }
}


/* Return false if we do not want to (or cannot) combine DEF.  */
static bool
can_combine_def_p (df_ref def)
{
  /* Do not consider if it is pre/post modification in MEM.  */
  if (DF_REF_FLAGS (def) & DF_REF_PRE_POST_MODIFY)
    return false;

  unsigned int regno = DF_REF_REGNO (def);

  /* Do not combine frame pointer adjustments.  */
  if ((regno == FRAME_POINTER_REGNUM
       && (!reload_completed || frame_pointer_needed))
      || (!HARD_FRAME_POINTER_IS_FRAME_POINTER
	  && regno == HARD_FRAME_POINTER_REGNUM
	  && (!reload_completed || frame_pointer_needed))
      || (FRAME_POINTER_REGNUM != ARG_POINTER_REGNUM
	  && regno == ARG_POINTER_REGNUM && fixed_regs[regno]))
    return false;

  return true;
}

/* Return false if we do not want to (or cannot) combine USE.  */
static bool
can_combine_use_p (df_ref use)
{
  /* Do not consider the usage of the stack pointer by function call.  */
  if (DF_REF_FLAGS (use) & DF_REF_CALL_STACK_USAGE)
    return false;

  return true;
}

/* Fill in log links field for all insns.  */

static void
create_log_links (void)
{
  basic_block bb;
  rtx_insn **next_use;
  rtx_insn *insn;
  df_ref def, use;

  next_use = XCNEWVEC (rtx_insn *, max_reg_num ());

  /* Pass through each block from the end, recording the uses of each
     register and establishing log links when def is encountered.
     Note that we do not clear next_use array in order to save time,
     so we have to test whether the use is in the same basic block as def.

     There are a few cases below when we do not consider the definition or
     usage -- these are taken from original flow.c did. Don't ask me why it is
     done this way; I don't know and if it works, I don't want to know.  */

  FOR_EACH_BB_FN (bb, cfun)
    {
      FOR_BB_INSNS_REVERSE (bb, insn)
        {
          if (!NONDEBUG_INSN_P (insn))
            continue;

	  /* Log links are created only once.  */
	  gcc_assert (!LOG_LINKS (insn));

	  FOR_EACH_INSN_DEF (def, insn)
            {
              unsigned int regno = DF_REF_REGNO (def);
              rtx_insn *use_insn;

              if (!next_use[regno])
                continue;

	      if (!can_combine_def_p (def))
		continue;

	      use_insn = next_use[regno];
	      next_use[regno] = NULL;

	      if (BLOCK_FOR_INSN (use_insn) != bb)
		continue;

	      /* flow.c claimed:

		 We don't build a LOG_LINK for hard registers contained
		 in ASM_OPERANDs.  If these registers get replaced,
		 we might wind up changing the semantics of the insn,
		 even if reload can make what appear to be valid
		 assignments later.  */
	      if (regno < FIRST_PSEUDO_REGISTER
		  && asm_noperands (PATTERN (use_insn)) >= 0)
		continue;

	      /* Don't add duplicate links between instructions.  */
	      struct insn_link *links;
	      FOR_EACH_LOG_LINK (links, use_insn)
	        if (insn == links->insn && regno == links->regno)
		  break;

	      if (!links)
		LOG_LINKS (use_insn)
		  = alloc_insn_link (insn, regno, LOG_LINKS (use_insn));
            }

	  FOR_EACH_INSN_USE (use, insn)
	    if (can_combine_use_p (use))
	      next_use[DF_REF_REGNO (use)] = insn;
        }
    }

  free (next_use);
}

/* Walk the LOG_LINKS of insn B to see if we find a reference to A.  Return
   true if we found a LOG_LINK that proves that A feeds B.  This only works
   if there are no instructions between A and B which could have a link
   depending on A, since in that case we would not record a link for B.
   We also check the implicit dependency created by a cc0 setter/user
   pair.  */

static bool
insn_a_feeds_b (rtx_insn *a, rtx_insn *b)
{
  struct insn_link *links;
  FOR_EACH_LOG_LINK (links, b)
    if (links->insn == a)
      return true;
  if (HAVE_cc0 && sets_cc0_p (a))
    return true;
  return false;
}

/* Main entry point for combiner.  F is the first insn of the function.
   NREGS is the first unused pseudo-reg number.

   Return nonzero if the combiner has turned an indirect jump
   instruction into a direct jump.  */
static int
combine_instructions (rtx_insn *f, unsigned int nregs)
{
  rtx_insn *insn, *next;
  rtx_insn *prev;
  struct insn_link *links, *nextlinks;
  rtx_insn *first;
  basic_block last_bb;

  int new_direct_jump_p = 0;

  for (first = f; first && !NONDEBUG_INSN_P (first); )
    first = NEXT_INSN (first);
  if (!first)
    return 0;

  combine_attempts = 0;
  combine_merges = 0;
  combine_extras = 0;
  combine_successes = 0;

  rtl_hooks = combine_rtl_hooks;

  reg_stat.safe_grow_cleared (nregs);

  init_recog_no_volatile ();

  /* Allocate array for insn info.  */
  max_uid_known = get_max_uid ();
  uid_log_links = XCNEWVEC (struct insn_link *, max_uid_known + 1);
  uid_insn_cost = XCNEWVEC (int, max_uid_known + 1);
  gcc_obstack_init (&insn_link_obstack);

  nonzero_bits_mode = int_mode_for_size (HOST_BITS_PER_WIDE_INT, 0).require ();

  /* Don't use reg_stat[].nonzero_bits when computing it.  This can cause
     problems when, for example, we have j <<= 1 in a loop.  */

  nonzero_sign_valid = 0;
  label_tick = label_tick_ebb_start = 1;

  /* Scan all SETs and see if we can deduce anything about what
     bits are known to be zero for some registers and how many copies
     of the sign bit are known to exist for those registers.

     Also set any known values so that we can use it while searching
     for what bits are known to be set.  */

  setup_incoming_promotions (first);
  /* Allow the entry block and the first block to fall into the same EBB.
     Conceptually the incoming promotions are assigned to the entry block.  */
  last_bb = ENTRY_BLOCK_PTR_FOR_FN (cfun);

  create_log_links ();
  FOR_EACH_BB_FN (this_basic_block, cfun)
    {
      optimize_this_for_speed_p = optimize_bb_for_speed_p (this_basic_block);
      last_call_luid = 0;
      mem_last_set = -1;

      label_tick++;
      if (!single_pred_p (this_basic_block)
	  || single_pred (this_basic_block) != last_bb)
	label_tick_ebb_start = label_tick;
      last_bb = this_basic_block;

      FOR_BB_INSNS (this_basic_block, insn)
        if (INSN_P (insn) && BLOCK_FOR_INSN (insn))
	  {
            rtx links;

            subst_low_luid = DF_INSN_LUID (insn);
            subst_insn = insn;

	    note_stores (PATTERN (insn), set_nonzero_bits_and_sign_copies,
		         insn);
	    record_dead_and_set_regs (insn);

	    if (AUTO_INC_DEC)
	      for (links = REG_NOTES (insn); links; links = XEXP (links, 1))
		if (REG_NOTE_KIND (links) == REG_INC)
		  set_nonzero_bits_and_sign_copies (XEXP (links, 0), NULL_RTX,
						    insn);

	    /* Record the current insn_cost of this instruction.  */
	    if (NONJUMP_INSN_P (insn))
	      INSN_COST (insn) = insn_cost (insn, optimize_this_for_speed_p);
	    if (dump_file)
	      {
		fprintf (dump_file, "insn_cost %d for ", INSN_COST (insn));
		dump_insn_slim (dump_file, insn);
	      }
	  }
    }

  nonzero_sign_valid = 1;

  /* Now scan all the insns in forward order.  */
  label_tick = label_tick_ebb_start = 1;
  init_reg_last ();
  setup_incoming_promotions (first);
  last_bb = ENTRY_BLOCK_PTR_FOR_FN (cfun);
  int max_combine = PARAM_VALUE (PARAM_MAX_COMBINE_INSNS);

  FOR_EACH_BB_FN (this_basic_block, cfun)
    {
      rtx_insn *last_combined_insn = NULL;

      /* Ignore instruction combination in basic blocks that are going to
	 be removed as unreachable anyway.  See PR82386.  */
      if (EDGE_COUNT (this_basic_block->preds) == 0)
	continue;

      optimize_this_for_speed_p = optimize_bb_for_speed_p (this_basic_block);
      last_call_luid = 0;
      mem_last_set = -1;

      label_tick++;
      if (!single_pred_p (this_basic_block)
	  || single_pred (this_basic_block) != last_bb)
	label_tick_ebb_start = label_tick;
      last_bb = this_basic_block;

      rtl_profile_for_bb (this_basic_block);
      for (insn = BB_HEAD (this_basic_block);
	   insn != NEXT_INSN (BB_END (this_basic_block));
	   insn = next ? next : NEXT_INSN (insn))
	{
	  next = 0;
	  if (!NONDEBUG_INSN_P (insn))
	    continue;

	  while (last_combined_insn
		 && (!NONDEBUG_INSN_P (last_combined_insn)
		     || last_combined_insn->deleted ()))
	    last_combined_insn = PREV_INSN (last_combined_insn);
	  if (last_combined_insn == NULL_RTX
	      || BLOCK_FOR_INSN (last_combined_insn) != this_basic_block
	      || DF_INSN_LUID (last_combined_insn) <= DF_INSN_LUID (insn))
	    last_combined_insn = insn;

	  /* See if we know about function return values before this
	     insn based upon SUBREG flags.  */
	  check_promoted_subreg (insn, PATTERN (insn));

	  /* See if we can find hardregs and subreg of pseudos in
	     narrower modes.  This could help turning TRUNCATEs
	     into SUBREGs.  */
	  note_uses (&PATTERN (insn), record_truncated_values, NULL);

	  /* Try this insn with each insn it links back to.  */

	  FOR_EACH_LOG_LINK (links, insn)
	    if ((next = try_combine (insn, links->insn, NULL,
				     NULL, &new_direct_jump_p,
				     last_combined_insn)) != 0)
	      {
		statistics_counter_event (cfun, "two-insn combine", 1);
		goto retry;
	      }

	  /* Try each sequence of three linked insns ending with this one.  */

	  if (max_combine >= 3)
	    FOR_EACH_LOG_LINK (links, insn)
	      {
		rtx_insn *link = links->insn;

		/* If the linked insn has been replaced by a note, then there
		   is no point in pursuing this chain any further.  */
		if (NOTE_P (link))
		  continue;

		FOR_EACH_LOG_LINK (nextlinks, link)
		  if ((next = try_combine (insn, link, nextlinks->insn,
					   NULL, &new_direct_jump_p,
					   last_combined_insn)) != 0)
		    {
		      statistics_counter_event (cfun, "three-insn combine", 1);
		      goto retry;
		    }
	      }

	  /* Try to combine a jump insn that uses CC0
	     with a preceding insn that sets CC0, and maybe with its
	     logical predecessor as well.
	     This is how we make decrement-and-branch insns.
	     We need this special code because data flow connections
	     via CC0 do not get entered in LOG_LINKS.  */

	  if (HAVE_cc0
	      && JUMP_P (insn)
	      && (prev = prev_nonnote_insn (insn)) != 0
	      && NONJUMP_INSN_P (prev)
	      && sets_cc0_p (PATTERN (prev)))
	    {
	      if ((next = try_combine (insn, prev, NULL, NULL,
				       &new_direct_jump_p,
				       last_combined_insn)) != 0)
		goto retry;

	      FOR_EACH_LOG_LINK (nextlinks, prev)
		  if ((next = try_combine (insn, prev, nextlinks->insn,
					   NULL, &new_direct_jump_p,
					   last_combined_insn)) != 0)
		    goto retry;
	    }

	  /* Do the same for an insn that explicitly references CC0.  */
	  if (HAVE_cc0 && NONJUMP_INSN_P (insn)
	      && (prev = prev_nonnote_insn (insn)) != 0
	      && NONJUMP_INSN_P (prev)
	      && sets_cc0_p (PATTERN (prev))
	      && GET_CODE (PATTERN (insn)) == SET
	      && reg_mentioned_p (cc0_rtx, SET_SRC (PATTERN (insn))))
	    {
	      if ((next = try_combine (insn, prev, NULL, NULL,
				       &new_direct_jump_p,
				       last_combined_insn)) != 0)
		goto retry;

	      FOR_EACH_LOG_LINK (nextlinks, prev)
		  if ((next = try_combine (insn, prev, nextlinks->insn,
					   NULL, &new_direct_jump_p,
					   last_combined_insn)) != 0)
		    goto retry;
	    }

	  /* Finally, see if any of the insns that this insn links to
	     explicitly references CC0.  If so, try this insn, that insn,
	     and its predecessor if it sets CC0.  */
	  if (HAVE_cc0)
	    {
	      FOR_EACH_LOG_LINK (links, insn)
		if (NONJUMP_INSN_P (links->insn)
		    && GET_CODE (PATTERN (links->insn)) == SET
		    && reg_mentioned_p (cc0_rtx, SET_SRC (PATTERN (links->insn)))
		    && (prev = prev_nonnote_insn (links->insn)) != 0
		    && NONJUMP_INSN_P (prev)
		    && sets_cc0_p (PATTERN (prev))
		    && (next = try_combine (insn, links->insn,
					    prev, NULL, &new_direct_jump_p,
					    last_combined_insn)) != 0)
		  goto retry;
	    }

	  /* Try combining an insn with two different insns whose results it
	     uses.  */
	  if (max_combine >= 3)
	    FOR_EACH_LOG_LINK (links, insn)
	      for (nextlinks = links->next; nextlinks;
		   nextlinks = nextlinks->next)
		if ((next = try_combine (insn, links->insn,
					 nextlinks->insn, NULL,
					 &new_direct_jump_p,
					 last_combined_insn)) != 0)

		  {
		    statistics_counter_event (cfun, "three-insn combine", 1);
		    goto retry;
		  }

	  /* Try four-instruction combinations.  */
	  if (max_combine >= 4)
	    FOR_EACH_LOG_LINK (links, insn)
	      {
		struct insn_link *next1;
		rtx_insn *link = links->insn;

		/* If the linked insn has been replaced by a note, then there
		   is no point in pursuing this chain any further.  */
		if (NOTE_P (link))
		  continue;

		FOR_EACH_LOG_LINK (next1, link)
		  {
		    rtx_insn *link1 = next1->insn;
		    if (NOTE_P (link1))
		      continue;
		    /* I0 -> I1 -> I2 -> I3.  */
		    FOR_EACH_LOG_LINK (nextlinks, link1)
		      if ((next = try_combine (insn, link, link1,
					       nextlinks->insn,
					       &new_direct_jump_p,
					       last_combined_insn)) != 0)
			{
			  statistics_counter_event (cfun, "four-insn combine", 1);
			  goto retry;
			}
		    /* I0, I1 -> I2, I2 -> I3.  */
		    for (nextlinks = next1->next; nextlinks;
			 nextlinks = nextlinks->next)
		      if ((next = try_combine (insn, link, link1,
					       nextlinks->insn,
					       &new_direct_jump_p,
					       last_combined_insn)) != 0)
			{
			  statistics_counter_event (cfun, "four-insn combine", 1);
			  goto retry;
			}
		  }

		for (next1 = links->next; next1; next1 = next1->next)
		  {
		    rtx_insn *link1 = next1->insn;
		    if (NOTE_P (link1))
		      continue;
		    /* I0 -> I2; I1, I2 -> I3.  */
		    FOR_EACH_LOG_LINK (nextlinks, link)
		      if ((next = try_combine (insn, link, link1,
					       nextlinks->insn,
					       &new_direct_jump_p,
					       last_combined_insn)) != 0)
			{
			  statistics_counter_event (cfun, "four-insn combine", 1);
			  goto retry;
			}
		    /* I0 -> I1; I1, I2 -> I3.  */
		    FOR_EACH_LOG_LINK (nextlinks, link1)
		      if ((next = try_combine (insn, link, link1,
					       nextlinks->insn,
					       &new_direct_jump_p,
					       last_combined_insn)) != 0)
			{
			  statistics_counter_event (cfun, "four-insn combine", 1);
			  goto retry;
			}
		  }
	      }

	  /* Try this insn with each REG_EQUAL note it links back to.  */
	  FOR_EACH_LOG_LINK (links, insn)
	    {
	      rtx set, note;
	      rtx_insn *temp = links->insn;
	      if ((set = single_set (temp)) != 0
		  && (note = find_reg_equal_equiv_note (temp)) != 0
		  && (note = XEXP (note, 0), GET_CODE (note)) != EXPR_LIST
		  /* Avoid using a register that may already been marked
		     dead by an earlier instruction.  */
		  && ! unmentioned_reg_p (note, SET_SRC (set))
		  && (GET_MODE (note) == VOIDmode
		      ? SCALAR_INT_MODE_P (GET_MODE (SET_DEST (set)))
		      : (GET_MODE (SET_DEST (set)) == GET_MODE (note)
			 && (GET_CODE (SET_DEST (set)) != ZERO_EXTRACT
			     || (GET_MODE (XEXP (SET_DEST (set), 0))
				 == GET_MODE (note))))))
		{
		  /* Temporarily replace the set's source with the
		     contents of the REG_EQUAL note.  The insn will
		     be deleted or recognized by try_combine.  */
		  rtx orig_src = SET_SRC (set);
		  rtx orig_dest = SET_DEST (set);
		  if (GET_CODE (SET_DEST (set)) == ZERO_EXTRACT)
		    SET_DEST (set) = XEXP (SET_DEST (set), 0);
		  SET_SRC (set) = note;
		  i2mod = temp;
		  i2mod_old_rhs = copy_rtx (orig_src);
		  i2mod_new_rhs = copy_rtx (note);
		  next = try_combine (insn, i2mod, NULL, NULL,
				      &new_direct_jump_p,
				      last_combined_insn);
		  i2mod = NULL;
		  if (next)
		    {
		      statistics_counter_event (cfun, "insn-with-note combine", 1);
		      goto retry;
		    }
		  SET_SRC (set) = orig_src;
		  SET_DEST (set) = orig_dest;
		}
	    }

	  if (!NOTE_P (insn))
	    record_dead_and_set_regs (insn);

retry:
	  ;
	}
    }

  default_rtl_profile ();
  clear_bb_flags ();
  new_direct_jump_p |= purge_all_dead_edges ();
  delete_noop_moves ();

  /* Clean up.  */
  obstack_free (&insn_link_obstack, NULL);
  free (uid_log_links);
  free (uid_insn_cost);
  reg_stat.release ();

  {
    struct undo *undo, *next;
    for (undo = undobuf.frees; undo; undo = next)
      {
	next = undo->next;
	free (undo);
      }
    undobuf.frees = 0;
  }

  total_attempts += combine_attempts;
  total_merges += combine_merges;
  total_extras += combine_extras;
  total_successes += combine_successes;

  nonzero_sign_valid = 0;
  rtl_hooks = general_rtl_hooks;

  /* Make recognizer allow volatile MEMs again.  */
  init_recog ();

  return new_direct_jump_p;
}

/* Wipe the last_xxx fields of reg_stat in preparation for another pass.  */

static void
init_reg_last (void)
{
  unsigned int i;
  reg_stat_type *p;

  FOR_EACH_VEC_ELT (reg_stat, i, p)
    memset (p, 0, offsetof (reg_stat_type, sign_bit_copies));
}

/* Set up any promoted values for incoming argument registers.  */

static void
setup_incoming_promotions (rtx_insn *first)
{
  tree arg;
  bool strictly_local = false;

  for (arg = DECL_ARGUMENTS (current_function_decl); arg;
       arg = DECL_CHAIN (arg))
    {
      rtx x, reg = DECL_INCOMING_RTL (arg);
      int uns1, uns3;
      machine_mode mode1, mode2, mode3, mode4;

      /* Only continue if the incoming argument is in a register.  */
      if (!REG_P (reg))
	continue;

      /* Determine, if possible, whether all call sites of the current
         function lie within the current compilation unit.  (This does
	 take into account the exporting of a function via taking its
	 address, and so forth.)  */
      strictly_local = cgraph_node::local_info (current_function_decl)->local;

      /* The mode and signedness of the argument before any promotions happen
         (equal to the mode of the pseudo holding it at that stage).  */
      mode1 = TYPE_MODE (TREE_TYPE (arg));
      uns1 = TYPE_UNSIGNED (TREE_TYPE (arg));

      /* The mode and signedness of the argument after any source language and
         TARGET_PROMOTE_PROTOTYPES-driven promotions.  */
      mode2 = TYPE_MODE (DECL_ARG_TYPE (arg));
      uns3 = TYPE_UNSIGNED (DECL_ARG_TYPE (arg));

      /* The mode and signedness of the argument as it is actually passed,
         see assign_parm_setup_reg in function.c.  */
      mode3 = promote_function_mode (TREE_TYPE (arg), mode1, &uns3,
				     TREE_TYPE (cfun->decl), 0);

      /* The mode of the register in which the argument is being passed.  */
      mode4 = GET_MODE (reg);

      /* Eliminate sign extensions in the callee when:
	 (a) A mode promotion has occurred;  */
      if (mode1 == mode3)
	continue;
      /* (b) The mode of the register is the same as the mode of
	     the argument as it is passed; */
      if (mode3 != mode4)
	continue;
      /* (c) There's no language level extension;  */
      if (mode1 == mode2)
	;
      /* (c.1) All callers are from the current compilation unit.  If that's
	 the case we don't have to rely on an ABI, we only have to know
	 what we're generating right now, and we know that we will do the
	 mode1 to mode2 promotion with the given sign.  */
      else if (!strictly_local)
	continue;
      /* (c.2) The combination of the two promotions is useful.  This is
	 true when the signs match, or if the first promotion is unsigned.
	 In the later case, (sign_extend (zero_extend x)) is the same as
	 (zero_extend (zero_extend x)), so make sure to force UNS3 true.  */
      else if (uns1)
	uns3 = true;
      else if (uns3)
	continue;

      /* Record that the value was promoted from mode1 to mode3,
	 so that any sign extension at the head of the current
	 function may be eliminated.  */
      x = gen_rtx_CLOBBER (mode1, const0_rtx);
      x = gen_rtx_fmt_e ((uns3 ? ZERO_EXTEND : SIGN_EXTEND), mode3, x);
      record_value_for_reg (reg, first, x);
    }
}

/* If MODE has a precision lower than PREC and SRC is a non-negative constant
   that would appear negative in MODE, sign-extend SRC for use in nonzero_bits
   because some machines (maybe most) will actually do the sign-extension and
   this is the conservative approach.

   ??? For 2.5, try to tighten up the MD files in this regard instead of this
   kludge.  */

static rtx
sign_extend_short_imm (rtx src, machine_mode mode, unsigned int prec)
{
  scalar_int_mode int_mode;
  if (CONST_INT_P (src)
      && is_a <scalar_int_mode> (mode, &int_mode)
      && GET_MODE_PRECISION (int_mode) < prec
      && INTVAL (src) > 0
      && val_signbit_known_set_p (int_mode, INTVAL (src)))
    src = GEN_INT (INTVAL (src) | ~GET_MODE_MASK (int_mode));

  return src;
}

/* Update RSP for pseudo-register X from INSN's REG_EQUAL note (if one exists)
   and SET.  */

static void
update_rsp_from_reg_equal (reg_stat_type *rsp, rtx_insn *insn, const_rtx set,
			   rtx x)
{
  rtx reg_equal_note = insn ? find_reg_equal_equiv_note (insn) : NULL_RTX;
  unsigned HOST_WIDE_INT bits = 0;
  rtx reg_equal = NULL, src = SET_SRC (set);
  unsigned int num = 0;

  if (reg_equal_note)
    reg_equal = XEXP (reg_equal_note, 0);

  if (SHORT_IMMEDIATES_SIGN_EXTEND)
    {
      src = sign_extend_short_imm (src, GET_MODE (x), BITS_PER_WORD);
      if (reg_equal)
	reg_equal = sign_extend_short_imm (reg_equal, GET_MODE (x), BITS_PER_WORD);
    }

  /* Don't call nonzero_bits if it cannot change anything.  */
  if (rsp->nonzero_bits != HOST_WIDE_INT_M1U)
    {
      bits = nonzero_bits (src, nonzero_bits_mode);
      if (reg_equal && bits)
	bits &= nonzero_bits (reg_equal, nonzero_bits_mode);
      rsp->nonzero_bits |= bits;
    }

  /* Don't call num_sign_bit_copies if it cannot change anything.  */
  if (rsp->sign_bit_copies != 1)
    {
      num = num_sign_bit_copies (SET_SRC (set), GET_MODE (x));
      if (reg_equal && maybe_ne (num, GET_MODE_PRECISION (GET_MODE (x))))
	{
	  unsigned int numeq = num_sign_bit_copies (reg_equal, GET_MODE (x));
	  if (num == 0 || numeq > num)
	    num = numeq;
	}
      if (rsp->sign_bit_copies == 0 || num < rsp->sign_bit_copies)
	rsp->sign_bit_copies = num;
    }
}

/* Called via note_stores.  If X is a pseudo that is narrower than
   HOST_BITS_PER_WIDE_INT and is being set, record what bits are known zero.

   If we are setting only a portion of X and we can't figure out what
   portion, assume all bits will be used since we don't know what will
   be happening.

   Similarly, set how many bits of X are known to be copies of the sign bit
   at all locations in the function.  This is the smallest number implied
   by any set of X.  */

static void
set_nonzero_bits_and_sign_copies (rtx x, const_rtx set, void *data)
{
  rtx_insn *insn = (rtx_insn *) data;
  scalar_int_mode mode;

  if (REG_P (x)
      && REGNO (x) >= FIRST_PSEUDO_REGISTER
      /* If this register is undefined at the start of the file, we can't
	 say what its contents were.  */
      && ! REGNO_REG_SET_P
	   (DF_LR_IN (ENTRY_BLOCK_PTR_FOR_FN (cfun)->next_bb), REGNO (x))
      && is_a <scalar_int_mode> (GET_MODE (x), &mode)
      && HWI_COMPUTABLE_MODE_P (mode))
    {
      reg_stat_type *rsp = &reg_stat[REGNO (x)];

      if (set == 0 || GET_CODE (set) == CLOBBER)
	{
	  rsp->nonzero_bits = GET_MODE_MASK (mode);
	  rsp->sign_bit_copies = 1;
	  return;
	}

      /* Should not happen as we only using pseduo registers.  */
      gcc_assert (GET_CODE (set) != CLOBBER_HIGH);

      /* If this register is being initialized using itself, and the
	 register is uninitialized in this basic block, and there are
	 no LOG_LINKS which set the register, then part of the
	 register is uninitialized.  In that case we can't assume
	 anything about the number of nonzero bits.

	 ??? We could do better if we checked this in
	 reg_{nonzero_bits,num_sign_bit_copies}_for_combine.  Then we
	 could avoid making assumptions about the insn which initially
	 sets the register, while still using the information in other
	 insns.  We would have to be careful to check every insn
	 involved in the combination.  */

      if (insn
	  && reg_referenced_p (x, PATTERN (insn))
	  && !REGNO_REG_SET_P (DF_LR_IN (BLOCK_FOR_INSN (insn)),
			       REGNO (x)))
	{
	  struct insn_link *link;

	  FOR_EACH_LOG_LINK (link, insn)
	    if (dead_or_set_p (link->insn, x))
	      break;
	  if (!link)
	    {
	      rsp->nonzero_bits = GET_MODE_MASK (mode);
	      rsp->sign_bit_copies = 1;
	      return;
	    }
	}

      /* If this is a complex assignment, see if we can convert it into a
	 simple assignment.  */
      set = expand_field_assignment (set);

      /* If this is a simple assignment, or we have a paradoxical SUBREG,
	 set what we know about X.  */

      if (SET_DEST (set) == x
	  || (paradoxical_subreg_p (SET_DEST (set))
	      && SUBREG_REG (SET_DEST (set)) == x))
	update_rsp_from_reg_equal (rsp, insn, set, x);
      else
	{
	  rsp->nonzero_bits = GET_MODE_MASK (mode);
	  rsp->sign_bit_copies = 1;
	}
    }
}

/* See if INSN can be combined into I3.  PRED, PRED2, SUCC and SUCC2 are
   optionally insns that were previously combined into I3 or that will be
   combined into the merger of INSN and I3.  The order is PRED, PRED2,
   INSN, SUCC, SUCC2, I3.

   Return 0 if the combination is not allowed for any reason.

   If the combination is allowed, *PDEST will be set to the single
   destination of INSN and *PSRC to the single source, and this function
   will return 1.  */

static int
can_combine_p (rtx_insn *insn, rtx_insn *i3, rtx_insn *pred ATTRIBUTE_UNUSED,
	       rtx_insn *pred2 ATTRIBUTE_UNUSED, rtx_insn *succ, rtx_insn *succ2,
	       rtx *pdest, rtx *psrc)
{
  int i;
  const_rtx set = 0;
  rtx src, dest;
  rtx_insn *p;
  rtx link;
  bool all_adjacent = true;
  int (*is_volatile_p) (const_rtx);

  if (succ)
    {
      if (succ2)
	{
	  if (next_active_insn (succ2) != i3)
	    all_adjacent = false;
	  if (next_active_insn (succ) != succ2)
	    all_adjacent = false;
	}
      else if (next_active_insn (succ) != i3)
	all_adjacent = false;
      if (next_active_insn (insn) != succ)
	all_adjacent = false;
    }
  else if (next_active_insn (insn) != i3)
    all_adjacent = false;
    
  /* Can combine only if previous insn is a SET of a REG, a SUBREG or CC0.
     or a PARALLEL consisting of such a SET and CLOBBERs.

     If INSN has CLOBBER parallel parts, ignore them for our processing.
     By definition, these happen during the execution of the insn.  When it
     is merged with another insn, all bets are off.  If they are, in fact,
     needed and aren't also supplied in I3, they may be added by
     recog_for_combine.  Otherwise, it won't match.

     We can also ignore a SET whose SET_DEST is mentioned in a REG_UNUSED
     note.

     Get the source and destination of INSN.  If more than one, can't
     combine.  */

  if (GET_CODE (PATTERN (insn)) == SET)
    set = PATTERN (insn);
  else if (GET_CODE (PATTERN (insn)) == PARALLEL
	   && GET_CODE (XVECEXP (PATTERN (insn), 0, 0)) == SET)
    {
      for (i = 0; i < XVECLEN (PATTERN (insn), 0); i++)
	{
	  rtx elt = XVECEXP (PATTERN (insn), 0, i);

	  switch (GET_CODE (elt))
	    {
	    /* This is important to combine floating point insns
	       for the SH4 port.  */
	    case USE:
	      /* Combining an isolated USE doesn't make sense.
		 We depend here on combinable_i3pat to reject them.  */
	      /* The code below this loop only verifies that the inputs of
		 the SET in INSN do not change.  We call reg_set_between_p
		 to verify that the REG in the USE does not change between
		 I3 and INSN.
		 If the USE in INSN was for a pseudo register, the matching
		 insn pattern will likely match any register; combining this
		 with any other USE would only be safe if we knew that the
		 used registers have identical values, or if there was
		 something to tell them apart, e.g. different modes.  For
		 now, we forgo such complicated tests and simply disallow
		 combining of USES of pseudo registers with any other USE.  */
	      if (REG_P (XEXP (elt, 0))
		  && GET_CODE (PATTERN (i3)) == PARALLEL)
		{
		  rtx i3pat = PATTERN (i3);
		  int i = XVECLEN (i3pat, 0) - 1;
		  unsigned int regno = REGNO (XEXP (elt, 0));

		  do
		    {
		      rtx i3elt = XVECEXP (i3pat, 0, i);

		      if (GET_CODE (i3elt) == USE
			  && REG_P (XEXP (i3elt, 0))
			  && (REGNO (XEXP (i3elt, 0)) == regno
			      ? reg_set_between_p (XEXP (elt, 0),
						   PREV_INSN (insn), i3)
			      : regno >= FIRST_PSEUDO_REGISTER))
			return 0;
		    }
		  while (--i >= 0);
		}
	      break;

	      /* We can ignore CLOBBERs.  */
	    case CLOBBER:
	    case CLOBBER_HIGH:
	      break;

	    case SET:
	      /* Ignore SETs whose result isn't used but not those that
		 have side-effects.  */
	      if (find_reg_note (insn, REG_UNUSED, SET_DEST (elt))
		  && insn_nothrow_p (insn)
		  && !side_effects_p (elt))
		break;

	      /* If we have already found a SET, this is a second one and
		 so we cannot combine with this insn.  */
	      if (set)
		return 0;

	      set = elt;
	      break;

	    default:
	      /* Anything else means we can't combine.  */
	      return 0;
	    }
	}

      if (set == 0
	  /* If SET_SRC is an ASM_OPERANDS we can't throw away these CLOBBERs,
	     so don't do anything with it.  */
	  || GET_CODE (SET_SRC (set)) == ASM_OPERANDS)
	return 0;
    }
  else
    return 0;

  if (set == 0)
    return 0;

  /* The simplification in expand_field_assignment may call back to
     get_last_value, so set safe guard here.  */
  subst_low_luid = DF_INSN_LUID (insn);

  set = expand_field_assignment (set);
  src = SET_SRC (set), dest = SET_DEST (set);

  /* Do not eliminate user-specified register if it is in an
     asm input because we may break the register asm usage defined
     in GCC manual if allow to do so.
     Be aware that this may cover more cases than we expect but this
     should be harmless.  */
  if (REG_P (dest) && REG_USERVAR_P (dest) && HARD_REGISTER_P (dest)
      && extract_asm_operands (PATTERN (i3)))
    return 0;

  /* Don't eliminate a store in the stack pointer.  */
  if (dest == stack_pointer_rtx
      /* Don't combine with an insn that sets a register to itself if it has
	 a REG_EQUAL note.  This may be part of a LIBCALL sequence.  */
      || (rtx_equal_p (src, dest) && find_reg_note (insn, REG_EQUAL, NULL_RTX))
      /* Can't merge an ASM_OPERANDS.  */
      || GET_CODE (src) == ASM_OPERANDS
      /* Can't merge a function call.  */
      || GET_CODE (src) == CALL
      /* Don't eliminate a function call argument.  */
      || (CALL_P (i3)
	  && (find_reg_fusage (i3, USE, dest)
	      || (REG_P (dest)
		  && REGNO (dest) < FIRST_PSEUDO_REGISTER
		  && global_regs[REGNO (dest)])))
      /* Don't substitute into an incremented register.  */
      || FIND_REG_INC_NOTE (i3, dest)
      || (succ && FIND_REG_INC_NOTE (succ, dest))
      || (succ2 && FIND_REG_INC_NOTE (succ2, dest))
      /* Don't substitute into a non-local goto, this confuses CFG.  */
      || (JUMP_P (i3) && find_reg_note (i3, REG_NON_LOCAL_GOTO, NULL_RTX))
      /* Make sure that DEST is not used after INSN but before SUCC, or
	 after SUCC and before SUCC2, or after SUCC2 but before I3.  */
      || (!all_adjacent
	  && ((succ2
	       && (reg_used_between_p (dest, succ2, i3)
		   || reg_used_between_p (dest, succ, succ2)))
	      || (!succ2 && succ && reg_used_between_p (dest, succ, i3))
	      || (!succ2 && !succ && reg_used_between_p (dest, insn, i3))
	      || (succ
		  /* SUCC and SUCC2 can be split halves from a PARALLEL; in
		     that case SUCC is not in the insn stream, so use SUCC2
		     instead for this test.  */
		  && reg_used_between_p (dest, insn,
					 succ2
					 && INSN_UID (succ) == INSN_UID (succ2)
					 ? succ2 : succ))))
      /* Make sure that the value that is to be substituted for the register
	 does not use any registers whose values alter in between.  However,
	 If the insns are adjacent, a use can't cross a set even though we
	 think it might (this can happen for a sequence of insns each setting
	 the same destination; last_set of that register might point to
	 a NOTE).  If INSN has a REG_EQUIV note, the register is always
	 equivalent to the memory so the substitution is valid even if there
	 are intervening stores.  Also, don't move a volatile asm or
	 UNSPEC_VOLATILE across any other insns.  */
      || (! all_adjacent
	  && (((!MEM_P (src)
		|| ! find_reg_note (insn, REG_EQUIV, src))
	       && modified_between_p (src, insn, i3))
	      || (GET_CODE (src) == ASM_OPERANDS && MEM_VOLATILE_P (src))
	      || GET_CODE (src) == UNSPEC_VOLATILE))
      /* Don't combine across a CALL_INSN, because that would possibly
	 change whether the life span of some REGs crosses calls or not,
	 and it is a pain to update that information.
	 Exception: if source is a constant, moving it later can't hurt.
	 Accept that as a special case.  */
      || (DF_INSN_LUID (insn) < last_call_luid && ! CONSTANT_P (src)))
    return 0;

  /* DEST must either be a REG or CC0.  */
  if (REG_P (dest))
    {
      /* If register alignment is being enforced for multi-word items in all
	 cases except for parameters, it is possible to have a register copy
	 insn referencing a hard register that is not allowed to contain the
	 mode being copied and which would not be valid as an operand of most
	 insns.  Eliminate this problem by not combining with such an insn.

	 Also, on some machines we don't want to extend the life of a hard
	 register.  */

      if (REG_P (src)
	  && ((REGNO (dest) < FIRST_PSEUDO_REGISTER
	       && !targetm.hard_regno_mode_ok (REGNO (dest), GET_MODE (dest)))
	      /* Don't extend the life of a hard register unless it is
		 user variable (if we have few registers) or it can't
		 fit into the desired register (meaning something special
		 is going on).
		 Also avoid substituting a return register into I3, because
		 reload can't handle a conflict with constraints of other
		 inputs.  */
	      || (REGNO (src) < FIRST_PSEUDO_REGISTER
		  && !targetm.hard_regno_mode_ok (REGNO (src),
						  GET_MODE (src)))))
	return 0;
    }
  else if (GET_CODE (dest) != CC0)
    return 0;


  if (GET_CODE (PATTERN (i3)) == PARALLEL)
    for (i = XVECLEN (PATTERN (i3), 0) - 1; i >= 0; i--)
      if (GET_CODE (XVECEXP (PATTERN (i3), 0, i)) == CLOBBER)
	{
	  rtx reg = XEXP (XVECEXP (PATTERN (i3), 0, i), 0);

	  /* If the clobber represents an earlyclobber operand, we must not
	     substitute an expression containing the clobbered register.
	     As we do not analyze the constraint strings here, we have to
	     make the conservative assumption.  However, if the register is
	     a fixed hard reg, the clobber cannot represent any operand;
	     we leave it up to the machine description to either accept or
	     reject use-and-clobber patterns.  */
	  if (!REG_P (reg)
	      || REGNO (reg) >= FIRST_PSEUDO_REGISTER
	      || !fixed_regs[REGNO (reg)])
	    if (reg_overlap_mentioned_p (reg, src))
	      return 0;
	}

  /* If INSN contains anything volatile, or is an `asm' (whether volatile
     or not), reject, unless nothing volatile comes between it and I3 */

  if (GET_CODE (src) == ASM_OPERANDS || volatile_refs_p (src))
    {
      /* Make sure neither succ nor succ2 contains a volatile reference.  */
      if (succ2 != 0 && volatile_refs_p (PATTERN (succ2)))
	return 0;
      if (succ != 0 && volatile_refs_p (PATTERN (succ)))
	return 0;
      /* We'll check insns between INSN and I3 below.  */
    }

  /* If INSN is an asm, and DEST is a hard register, reject, since it has
     to be an explicit register variable, and was chosen for a reason.  */

  if (GET_CODE (src) == ASM_OPERANDS
      && REG_P (dest) && REGNO (dest) < FIRST_PSEUDO_REGISTER)
    return 0;

  /* If INSN contains volatile references (specifically volatile MEMs),
     we cannot combine across any other volatile references.
     Even if INSN doesn't contain volatile references, any intervening
     volatile insn might affect machine state.  */

  is_volatile_p = volatile_refs_p (PATTERN (insn))
    ? volatile_refs_p
    : volatile_insn_p;
    
  for (p = NEXT_INSN (insn); p != i3; p = NEXT_INSN (p))
    if (INSN_P (p) && p != succ && p != succ2 && is_volatile_p (PATTERN (p)))
      return 0;

  /* If INSN contains an autoincrement or autodecrement, make sure that
     register is not used between there and I3, and not already used in
     I3 either.  Neither must it be used in PRED or SUCC, if they exist.
     Also insist that I3 not be a jump; if it were one
     and the incremented register were spilled, we would lose.  */

  if (AUTO_INC_DEC)
    for (link = REG_NOTES (insn); link; link = XEXP (link, 1))
      if (REG_NOTE_KIND (link) == REG_INC
	  && (JUMP_P (i3)
	      || reg_used_between_p (XEXP (link, 0), insn, i3)
	      || (pred != NULL_RTX
		  && reg_overlap_mentioned_p (XEXP (link, 0), PATTERN (pred)))
	      || (pred2 != NULL_RTX
		  && reg_overlap_mentioned_p (XEXP (link, 0), PATTERN (pred2)))
	      || (succ != NULL_RTX
		  && reg_overlap_mentioned_p (XEXP (link, 0), PATTERN (succ)))
	      || (succ2 != NULL_RTX
		  && reg_overlap_mentioned_p (XEXP (link, 0), PATTERN (succ2)))
	      || reg_overlap_mentioned_p (XEXP (link, 0), PATTERN (i3))))
	return 0;

  /* Don't combine an insn that follows a CC0-setting insn.
     An insn that uses CC0 must not be separated from the one that sets it.
     We do, however, allow I2 to follow a CC0-setting insn if that insn
     is passed as I1; in that case it will be deleted also.
     We also allow combining in this case if all the insns are adjacent
     because that would leave the two CC0 insns adjacent as well.
     It would be more logical to test whether CC0 occurs inside I1 or I2,
     but that would be much slower, and this ought to be equivalent.  */

  if (HAVE_cc0)
    {
      p = prev_nonnote_insn (insn);
      if (p && p != pred && NONJUMP_INSN_P (p) && sets_cc0_p (PATTERN (p))
	  && ! all_adjacent)
	return 0;
    }

  /* If we get here, we have passed all the tests and the combination is
     to be allowed.  */

  *pdest = dest;
  *psrc = src;

  return 1;
}

/* LOC is the location within I3 that contains its pattern or the component
   of a PARALLEL of the pattern.  We validate that it is valid for combining.

   One problem is if I3 modifies its output, as opposed to replacing it
   entirely, we can't allow the output to contain I2DEST, I1DEST or I0DEST as
   doing so would produce an insn that is not equivalent to the original insns.

   Consider:

	 (set (reg:DI 101) (reg:DI 100))
	 (set (subreg:SI (reg:DI 101) 0) <foo>)

   This is NOT equivalent to:

	 (parallel [(set (subreg:SI (reg:DI 100) 0) <foo>)
		    (set (reg:DI 101) (reg:DI 100))])

   Not only does this modify 100 (in which case it might still be valid
   if 100 were dead in I2), it sets 101 to the ORIGINAL value of 100.

   We can also run into a problem if I2 sets a register that I1
   uses and I1 gets directly substituted into I3 (not via I2).  In that
   case, we would be getting the wrong value of I2DEST into I3, so we
   must reject the combination.  This case occurs when I2 and I1 both
   feed into I3, rather than when I1 feeds into I2, which feeds into I3.
   If I1_NOT_IN_SRC is nonzero, it means that finding I1 in the source
   of a SET must prevent combination from occurring.  The same situation
   can occur for I0, in which case I0_NOT_IN_SRC is set.

   Before doing the above check, we first try to expand a field assignment
   into a set of logical operations.

   If PI3_DEST_KILLED is nonzero, it is a pointer to a location in which
   we place a register that is both set and used within I3.  If more than one
   such register is detected, we fail.

   Return 1 if the combination is valid, zero otherwise.  */

static int
combinable_i3pat (rtx_insn *i3, rtx *loc, rtx i2dest, rtx i1dest, rtx i0dest,
		  int i1_not_in_src, int i0_not_in_src, rtx *pi3dest_killed)
{
  rtx x = *loc;

  if (GET_CODE (x) == SET)
    {
      rtx set = x ;
      rtx dest = SET_DEST (set);
      rtx src = SET_SRC (set);
      rtx inner_dest = dest;
      rtx subdest;

      while (GET_CODE (inner_dest) == STRICT_LOW_PART
	     || GET_CODE (inner_dest) == SUBREG
	     || GET_CODE (inner_dest) == ZERO_EXTRACT)
	inner_dest = XEXP (inner_dest, 0);

      /* Check for the case where I3 modifies its output, as discussed
	 above.  We don't want to prevent pseudos from being combined
	 into the address of a MEM, so only prevent the combination if
	 i1 or i2 set the same MEM.  */
      if ((inner_dest != dest &&
	   (!MEM_P (inner_dest)
	    || rtx_equal_p (i2dest, inner_dest)
	    || (i1dest && rtx_equal_p (i1dest, inner_dest))
	    || (i0dest && rtx_equal_p (i0dest, inner_dest)))
	   && (reg_overlap_mentioned_p (i2dest, inner_dest)
	       || (i1dest && reg_overlap_mentioned_p (i1dest, inner_dest))
	       || (i0dest && reg_overlap_mentioned_p (i0dest, inner_dest))))

	  /* This is the same test done in can_combine_p except we can't test
	     all_adjacent; we don't have to, since this instruction will stay
	     in place, thus we are not considering increasing the lifetime of
	     INNER_DEST.

	     Also, if this insn sets a function argument, combining it with
	     something that might need a spill could clobber a previous
	     function argument; the all_adjacent test in can_combine_p also
	     checks this; here, we do a more specific test for this case.  */

	  || (REG_P (inner_dest)
	      && REGNO (inner_dest) < FIRST_PSEUDO_REGISTER
	      && !targetm.hard_regno_mode_ok (REGNO (inner_dest),
					      GET_MODE (inner_dest)))
	  || (i1_not_in_src && reg_overlap_mentioned_p (i1dest, src))
	  || (i0_not_in_src && reg_overlap_mentioned_p (i0dest, src)))
	return 0;

      /* If DEST is used in I3, it is being killed in this insn, so
	 record that for later.  We have to consider paradoxical
	 subregs here, since they kill the whole register, but we
	 ignore partial subregs, STRICT_LOW_PART, etc.
	 Never add REG_DEAD notes for the FRAME_POINTER_REGNUM or the
	 STACK_POINTER_REGNUM, since these are always considered to be
	 live.  Similarly for ARG_POINTER_REGNUM if it is fixed.  */
      subdest = dest;
      if (GET_CODE (subdest) == SUBREG && !partial_subreg_p (subdest))
	subdest = SUBREG_REG (subdest);
      if (pi3dest_killed
	  && REG_P (subdest)
	  && reg_referenced_p (subdest, PATTERN (i3))
	  && REGNO (subdest) != FRAME_POINTER_REGNUM
	  && (HARD_FRAME_POINTER_IS_FRAME_POINTER
	      || REGNO (subdest) != HARD_FRAME_POINTER_REGNUM)
	  && (FRAME_POINTER_REGNUM == ARG_POINTER_REGNUM
	      || (REGNO (subdest) != ARG_POINTER_REGNUM
		  || ! fixed_regs [REGNO (subdest)]))
	  && REGNO (subdest) != STACK_POINTER_REGNUM)
	{
	  if (*pi3dest_killed)
	    return 0;

	  *pi3dest_killed = subdest;
	}
    }

  else if (GET_CODE (x) == PARALLEL)
    {
      int i;

      for (i = 0; i < XVECLEN (x, 0); i++)
	if (! combinable_i3pat (i3, &XVECEXP (x, 0, i), i2dest, i1dest, i0dest,
				i1_not_in_src, i0_not_in_src, pi3dest_killed))
	  return 0;
    }

  return 1;
}

/* Return 1 if X is an arithmetic expression that contains a multiplication
   and division.  We don't count multiplications by powers of two here.  */

static int
contains_muldiv (rtx x)
{
  switch (GET_CODE (x))
    {
    case MOD:  case DIV:  case UMOD:  case UDIV:
      return 1;

    case MULT:
      return ! (CONST_INT_P (XEXP (x, 1))
		&& pow2p_hwi (UINTVAL (XEXP (x, 1))));
    default:
      if (BINARY_P (x))
	return contains_muldiv (XEXP (x, 0))
	    || contains_muldiv (XEXP (x, 1));

      if (UNARY_P (x))
	return contains_muldiv (XEXP (x, 0));

      return 0;
    }
}

/* Determine whether INSN can be used in a combination.  Return nonzero if
   not.  This is used in try_combine to detect early some cases where we
   can't perform combinations.  */

static int
cant_combine_insn_p (rtx_insn *insn)
{
  rtx set;
  rtx src, dest;

  /* If this isn't really an insn, we can't do anything.
     This can occur when flow deletes an insn that it has merged into an
     auto-increment address.  */
  if (!NONDEBUG_INSN_P (insn))
    return 1;

  /* Never combine loads and stores involving hard regs that are likely
     to be spilled.  The register allocator can usually handle such
     reg-reg moves by tying.  If we allow the combiner to make
     substitutions of likely-spilled regs, reload might die.
     As an exception, we allow combinations involving fixed regs; these are
     not available to the register allocator so there's no risk involved.  */

  set = single_set (insn);
  if (! set)
    return 0;
  src = SET_SRC (set);
  dest = SET_DEST (set);
  if (GET_CODE (src) == SUBREG)
    src = SUBREG_REG (src);
  if (GET_CODE (dest) == SUBREG)
    dest = SUBREG_REG (dest);
  if (REG_P (src) && REG_P (dest)
      && ((HARD_REGISTER_P (src)
	   && ! TEST_HARD_REG_BIT (fixed_reg_set, REGNO (src)))
	  || (HARD_REGISTER_P (dest)
	      && ! TEST_HARD_REG_BIT (fixed_reg_set, REGNO (dest))
	      && targetm.class_likely_spilled_p (REGNO_REG_CLASS (REGNO (dest))))))
    return 1;

  return 0;
}

struct likely_spilled_retval_info
{
  unsigned regno, nregs;
  unsigned mask;
};

/* Called via note_stores by likely_spilled_retval_p.  Remove from info->mask
   hard registers that are known to be written to / clobbered in full.  */
static void
likely_spilled_retval_1 (rtx x, const_rtx set, void *data)
{
  struct likely_spilled_retval_info *const info =
    (struct likely_spilled_retval_info *) data;
  unsigned regno, nregs;
  unsigned new_mask;

  if (!REG_P (XEXP (set, 0)))
    return;
  regno = REGNO (x);
  if (regno >= info->regno + info->nregs)
    return;
  nregs = REG_NREGS (x);
  if (regno + nregs <= info->regno)
    return;
  new_mask = (2U << (nregs - 1)) - 1;
  if (regno < info->regno)
    new_mask >>= info->regno - regno;
  else
    new_mask <<= regno - info->regno;
  info->mask &= ~new_mask;
}

/* Return nonzero iff part of the return value is live during INSN, and
   it is likely spilled.  This can happen when more than one insn is needed
   to copy the return value, e.g. when we consider to combine into the
   second copy insn for a complex value.  */

static int
likely_spilled_retval_p (rtx_insn *insn)
{
  rtx_insn *use = BB_END (this_basic_block);
  rtx reg;
  rtx_insn *p;
  unsigned regno, nregs;
  /* We assume here that no machine mode needs more than
     32 hard registers when the value overlaps with a register
     for which TARGET_FUNCTION_VALUE_REGNO_P is true.  */
  unsigned mask;
  struct likely_spilled_retval_info info;

  if (!NONJUMP_INSN_P (use) || GET_CODE (PATTERN (use)) != USE || insn == use)
    return 0;
  reg = XEXP (PATTERN (use), 0);
  if (!REG_P (reg) || !targetm.calls.function_value_regno_p (REGNO (reg)))
    return 0;
  regno = REGNO (reg);
  nregs = REG_NREGS (reg);
  if (nregs == 1)
    return 0;
  mask = (2U << (nregs - 1)) - 1;

  /* Disregard parts of the return value that are set later.  */
  info.regno = regno;
  info.nregs = nregs;
  info.mask = mask;
  for (p = PREV_INSN (use); info.mask && p != insn; p = PREV_INSN (p))
    if (INSN_P (p))
      note_stores (PATTERN (p), likely_spilled_retval_1, &info);
  mask = info.mask;

  /* Check if any of the (probably) live return value registers is
     likely spilled.  */
  nregs --;
  do
    {
      if ((mask & 1 << nregs)
	  && targetm.class_likely_spilled_p (REGNO_REG_CLASS (regno + nregs)))
	return 1;
    } while (nregs--);
  return 0;
}

/* Adjust INSN after we made a change to its destination.

   Changing the destination can invalidate notes that say something about
   the results of the insn and a LOG_LINK pointing to the insn.  */

static void
adjust_for_new_dest (rtx_insn *insn)
{
  /* For notes, be conservative and simply remove them.  */
  remove_reg_equal_equiv_notes (insn);

  /* The new insn will have a destination that was previously the destination
     of an insn just above it.  Call distribute_links to make a LOG_LINK from
     the next use of that destination.  */

  rtx set = single_set (insn);
  gcc_assert (set);

  rtx reg = SET_DEST (set);

  while (GET_CODE (reg) == ZERO_EXTRACT
	 || GET_CODE (reg) == STRICT_LOW_PART
	 || GET_CODE (reg) == SUBREG)
    reg = XEXP (reg, 0);
  gcc_assert (REG_P (reg));

  distribute_links (alloc_insn_link (insn, REGNO (reg), NULL));

  df_insn_rescan (insn);
}

/* Return TRUE if combine can reuse reg X in mode MODE.
   ADDED_SETS is nonzero if the original set is still required.  */
static bool
can_change_dest_mode (rtx x, int added_sets, machine_mode mode)
{
  unsigned int regno;

  if (!REG_P (x))
    return false;

  /* Don't change between modes with different underlying register sizes,
     since this could lead to invalid subregs.  */
  if (maybe_ne (REGMODE_NATURAL_SIZE (mode),
		REGMODE_NATURAL_SIZE (GET_MODE (x))))
    return false;

  regno = REGNO (x);
  /* Allow hard registers if the new mode is legal, and occupies no more
     registers than the old mode.  */
  if (regno < FIRST_PSEUDO_REGISTER)
    return (targetm.hard_regno_mode_ok (regno, mode)
	    && REG_NREGS (x) >= hard_regno_nregs (regno, mode));

  /* Or a pseudo that is only used once.  */
  return (regno < reg_n_sets_max
	  && REG_N_SETS (regno) == 1
	  && !added_sets
	  && !REG_USERVAR_P (x));
}


/* Check whether X, the destination of a set, refers to part of
   the register specified by REG.  */

static bool
reg_subword_p (rtx x, rtx reg)
{
  /* Check that reg is an integer mode register.  */
  if (!REG_P (reg) || GET_MODE_CLASS (GET_MODE (reg)) != MODE_INT)
    return false;

  if (GET_CODE (x) == STRICT_LOW_PART
      || GET_CODE (x) == ZERO_EXTRACT)
    x = XEXP (x, 0);

  return GET_CODE (x) == SUBREG
	 && SUBREG_REG (x) == reg
	 && GET_MODE_CLASS (GET_MODE (x)) == MODE_INT;
}

/* Delete the unconditional jump INSN and adjust the CFG correspondingly.
   Note that the INSN should be deleted *after* removing dead edges, so
   that the kept edge is the fallthrough edge for a (set (pc) (pc))
   but not for a (set (pc) (label_ref FOO)).  */

static void
update_cfg_for_uncondjump (rtx_insn *insn)
{
  basic_block bb = BLOCK_FOR_INSN (insn);
  gcc_assert (BB_END (bb) == insn);

  purge_dead_edges (bb);

  delete_insn (insn);
  if (EDGE_COUNT (bb->succs) == 1)
    {
      rtx_insn *insn;

      single_succ_edge (bb)->flags |= EDGE_FALLTHRU;

      /* Remove barriers from the footer if there are any.  */
      for (insn = BB_FOOTER (bb); insn; insn = NEXT_INSN (insn))
	if (BARRIER_P (insn))
	  {
	    if (PREV_INSN (insn))
	      SET_NEXT_INSN (PREV_INSN (insn)) = NEXT_INSN (insn);
	    else
	      BB_FOOTER (bb) = NEXT_INSN (insn);
	    if (NEXT_INSN (insn))
	      SET_PREV_INSN (NEXT_INSN (insn)) = PREV_INSN (insn);
	  }
	else if (LABEL_P (insn))
	  break;
    }
}

/* Return whether PAT is a PARALLEL of exactly N register SETs followed
   by an arbitrary number of CLOBBERs.  */
static bool
is_parallel_of_n_reg_sets (rtx pat, int n)
{
  if (GET_CODE (pat) != PARALLEL)
    return false;

  int len = XVECLEN (pat, 0);
  if (len < n)
    return false;

  int i;
  for (i = 0; i < n; i++)
    if (GET_CODE (XVECEXP (pat, 0, i)) != SET
	|| !REG_P (SET_DEST (XVECEXP (pat, 0, i))))
      return false;
  for ( ; i < len; i++)
    switch (GET_CODE (XVECEXP (pat, 0, i)))
      {
      case CLOBBER:
	if (XEXP (XVECEXP (pat, 0, i), 0) == const0_rtx)
	  return false;
	break;
      case CLOBBER_HIGH:
	break;
      default:
	return false;
      }
  return true;
}

/* Return whether INSN, a PARALLEL of N register SETs (and maybe some
   CLOBBERs), can be split into individual SETs in that order, without
   changing semantics.  */
static bool
can_split_parallel_of_n_reg_sets (rtx_insn *insn, int n)
{
  if (!insn_nothrow_p (insn))
    return false;

  rtx pat = PATTERN (insn);

  int i, j;
  for (i = 0; i < n; i++)
    {
      if (side_effects_p (SET_SRC (XVECEXP (pat, 0, i))))
	return false;

      rtx reg = SET_DEST (XVECEXP (pat, 0, i));

      for (j = i + 1; j < n; j++)
	if (reg_referenced_p (reg, XVECEXP (pat, 0, j)))
	  return false;
    }

  return true;
}

/* Return whether X is just a single set, with the source
   a general_operand.  */
static bool
is_just_move (rtx x)
{
  if (INSN_P (x))
    x = PATTERN (x);

  return (GET_CODE (x) == SET && general_operand (SET_SRC (x), VOIDmode));
}

/* Try to combine the insns I0, I1 and I2 into I3.
   Here I0, I1 and I2 appear earlier than I3.
   I0 and I1 can be zero; then we combine just I2 into I3, or I1 and I2 into
   I3.

   If we are combining more than two insns and the resulting insn is not
   recognized, try splitting it into two insns.  If that happens, I2 and I3
   are retained and I1/I0 are pseudo-deleted by turning them into a NOTE.
   Otherwise, I0, I1 and I2 are pseudo-deleted.

   Return 0 if the combination does not work.  Then nothing is changed.
   If we did the combination, return the insn at which combine should
   resume scanning.

   Set NEW_DIRECT_JUMP_P to a nonzero value if try_combine creates a
   new direct jump instruction.

   LAST_COMBINED_INSN is either I3, or some insn after I3 that has
   been I3 passed to an earlier try_combine within the same basic
   block.  */

static rtx_insn *
try_combine (rtx_insn *i3, rtx_insn *i2, rtx_insn *i1, rtx_insn *i0,
	     int *new_direct_jump_p, rtx_insn *last_combined_insn)
{
  /* New patterns for I3 and I2, respectively.  */
  rtx newpat, newi2pat = 0;
  rtvec newpat_vec_with_clobbers = 0;
  int substed_i2 = 0, substed_i1 = 0, substed_i0 = 0;
  /* Indicates need to preserve SET in I0, I1 or I2 in I3 if it is not
     dead.  */
  int added_sets_0, added_sets_1, added_sets_2;
  /* Total number of SETs to put into I3.  */
  int total_sets;
  /* Nonzero if I2's or I1's body now appears in I3.  */
  int i2_is_used = 0, i1_is_used = 0;
  /* INSN_CODEs for new I3, new I2, and user of condition code.  */
  int insn_code_number, i2_code_number = 0, other_code_number = 0;
  /* Contains I3 if the destination of I3 is used in its source, which means
     that the old life of I3 is being killed.  If that usage is placed into
     I2 and not in I3, a REG_DEAD note must be made.  */
  rtx i3dest_killed = 0;
  /* SET_DEST and SET_SRC of I2, I1 and I0.  */
  rtx i2dest = 0, i2src = 0, i1dest = 0, i1src = 0, i0dest = 0, i0src = 0;
  /* Copy of SET_SRC of I1 and I0, if needed.  */
  rtx i1src_copy = 0, i0src_copy = 0, i0src_copy2 = 0;
  /* Set if I2DEST was reused as a scratch register.  */
  bool i2scratch = false;
  /* The PATTERNs of I0, I1, and I2, or a copy of them in certain cases.  */
  rtx i0pat = 0, i1pat = 0, i2pat = 0;
  /* Indicates if I2DEST or I1DEST is in I2SRC or I1_SRC.  */
  int i2dest_in_i2src = 0, i1dest_in_i1src = 0, i2dest_in_i1src = 0;
  int i0dest_in_i0src = 0, i1dest_in_i0src = 0, i2dest_in_i0src = 0;
  int i2dest_killed = 0, i1dest_killed = 0, i0dest_killed = 0;
  int i1_feeds_i2_n = 0, i0_feeds_i2_n = 0, i0_feeds_i1_n = 0;
  /* Notes that must be added to REG_NOTES in I3 and I2.  */
  rtx new_i3_notes, new_i2_notes;
  /* Notes that we substituted I3 into I2 instead of the normal case.  */
  int i3_subst_into_i2 = 0;
  /* Notes that I1, I2 or I3 is a MULT operation.  */
  int have_mult = 0;
  int swap_i2i3 = 0;
  int split_i2i3 = 0;
  int changed_i3_dest = 0;
  bool i2_was_move = false, i3_was_move = false;

  int maxreg;
  rtx_insn *temp_insn;
  rtx temp_expr;
  struct insn_link *link;
  rtx other_pat = 0;
  rtx new_other_notes;
  int i;
  scalar_int_mode dest_mode, temp_mode;

  /* Immediately return if any of I0,I1,I2 are the same insn (I3 can
     never be).  */
  if (i1 == i2 || i0 == i2 || (i0 && i0 == i1))
    return 0;

  /* Only try four-insn combinations when there's high likelihood of
     success.  Look for simple insns, such as loads of constants or
     binary operations involving a constant.  */
  if (i0)
    {
      int i;
      int ngood = 0;
      int nshift = 0;
      rtx set0, set3;

      if (!flag_expensive_optimizations)
	return 0;

      for (i = 0; i < 4; i++)
	{
	  rtx_insn *insn = i == 0 ? i0 : i == 1 ? i1 : i == 2 ? i2 : i3;
	  rtx set = single_set (insn);
	  rtx src;
	  if (!set)
	    continue;
	  src = SET_SRC (set);
	  if (CONSTANT_P (src))
	    {
	      ngood += 2;
	      break;
	    }
	  else if (BINARY_P (src) && CONSTANT_P (XEXP (src, 1)))
	    ngood++;
	  else if (GET_CODE (src) == ASHIFT || GET_CODE (src) == ASHIFTRT
		   || GET_CODE (src) == LSHIFTRT)
	    nshift++;
	}

      /* If I0 loads a memory and I3 sets the same memory, then I1 and I2
	 are likely manipulating its value.  Ideally we'll be able to combine
	 all four insns into a bitfield insertion of some kind. 

	 Note the source in I0 might be inside a sign/zero extension and the
	 memory modes in I0 and I3 might be different.  So extract the address
	 from the destination of I3 and search for it in the source of I0.

	 In the event that there's a match but the source/dest do not actually
	 refer to the same memory, the worst that happens is we try some
	 combinations that we wouldn't have otherwise.  */
      if ((set0 = single_set (i0))
	  /* Ensure the source of SET0 is a MEM, possibly buried inside
	     an extension.  */
	  && (GET_CODE (SET_SRC (set0)) == MEM
	      || ((GET_CODE (SET_SRC (set0)) == ZERO_EXTEND
		   || GET_CODE (SET_SRC (set0)) == SIGN_EXTEND)
		  && GET_CODE (XEXP (SET_SRC (set0), 0)) == MEM))
	  && (set3 = single_set (i3))
	  /* Ensure the destination of SET3 is a MEM.  */
	  && GET_CODE (SET_DEST (set3)) == MEM
	  /* Would it be better to extract the base address for the MEM
	     in SET3 and look for that?  I don't have cases where it matters
	     but I could envision such cases.  */
	  && rtx_referenced_p (XEXP (SET_DEST (set3), 0), SET_SRC (set0)))
	ngood += 2;

      if (ngood < 2 && nshift < 2)
	return 0;
    }

  /* Exit early if one of the insns involved can't be used for
     combinations.  */
  if (CALL_P (i2)
      || (i1 && CALL_P (i1))
      || (i0 && CALL_P (i0))
      || cant_combine_insn_p (i3)
      || cant_combine_insn_p (i2)
      || (i1 && cant_combine_insn_p (i1))
      || (i0 && cant_combine_insn_p (i0))
      || likely_spilled_retval_p (i3))
    return 0;

  combine_attempts++;
  undobuf.other_insn = 0;

  /* Reset the hard register usage information.  */
  CLEAR_HARD_REG_SET (newpat_used_regs);

  if (dump_file && (dump_flags & TDF_DETAILS))
    {
      if (i0)
	fprintf (dump_file, "\nTrying %d, %d, %d -> %d:\n",
		 INSN_UID (i0), INSN_UID (i1), INSN_UID (i2), INSN_UID (i3));
      else if (i1)
	fprintf (dump_file, "\nTrying %d, %d -> %d:\n",
		 INSN_UID (i1), INSN_UID (i2), INSN_UID (i3));
      else
	fprintf (dump_file, "\nTrying %d -> %d:\n",
		 INSN_UID (i2), INSN_UID (i3));

      if (i0)
	dump_insn_slim (dump_file, i0);
      if (i1)
	dump_insn_slim (dump_file, i1);
      dump_insn_slim (dump_file, i2);
      dump_insn_slim (dump_file, i3);
    }

  /* If multiple insns feed into one of I2 or I3, they can be in any
     order.  To simplify the code below, reorder them in sequence.  */
  if (i0 && DF_INSN_LUID (i0) > DF_INSN_LUID (i2))
    std::swap (i0, i2);
  if (i0 && DF_INSN_LUID (i0) > DF_INSN_LUID (i1))
    std::swap (i0, i1);
  if (i1 && DF_INSN_LUID (i1) > DF_INSN_LUID (i2))
    std::swap (i1, i2);

  added_links_insn = 0;
  added_notes_insn = 0;

  /* First check for one important special case that the code below will
     not handle.  Namely, the case where I1 is zero, I2 is a PARALLEL
     and I3 is a SET whose SET_SRC is a SET_DEST in I2.  In that case,
     we may be able to replace that destination with the destination of I3.
     This occurs in the common code where we compute both a quotient and
     remainder into a structure, in which case we want to do the computation
     directly into the structure to avoid register-register copies.

     Note that this case handles both multiple sets in I2 and also cases
     where I2 has a number of CLOBBERs inside the PARALLEL.

     We make very conservative checks below and only try to handle the
     most common cases of this.  For example, we only handle the case
     where I2 and I3 are adjacent to avoid making difficult register
     usage tests.  */

  if (i1 == 0 && NONJUMP_INSN_P (i3) && GET_CODE (PATTERN (i3)) == SET
      && REG_P (SET_SRC (PATTERN (i3)))
      && REGNO (SET_SRC (PATTERN (i3))) >= FIRST_PSEUDO_REGISTER
      && find_reg_note (i3, REG_DEAD, SET_SRC (PATTERN (i3)))
      && GET_CODE (PATTERN (i2)) == PARALLEL
      && ! side_effects_p (SET_DEST (PATTERN (i3)))
      /* If the dest of I3 is a ZERO_EXTRACT or STRICT_LOW_PART, the code
	 below would need to check what is inside (and reg_overlap_mentioned_p
	 doesn't support those codes anyway).  Don't allow those destinations;
	 the resulting insn isn't likely to be recognized anyway.  */
      && GET_CODE (SET_DEST (PATTERN (i3))) != ZERO_EXTRACT
      && GET_CODE (SET_DEST (PATTERN (i3))) != STRICT_LOW_PART
      && ! reg_overlap_mentioned_p (SET_SRC (PATTERN (i3)),
				    SET_DEST (PATTERN (i3)))
      && next_active_insn (i2) == i3)
    {
      rtx p2 = PATTERN (i2);

      /* Make sure that the destination of I3,
	 which we are going to substitute into one output of I2,
	 is not used within another output of I2.  We must avoid making this:
	 (parallel [(set (mem (reg 69)) ...)
		    (set (reg 69) ...)])
	 which is not well-defined as to order of actions.
	 (Besides, reload can't handle output reloads for this.)

	 The problem can also happen if the dest of I3 is a memory ref,
	 if another dest in I2 is an indirect memory ref.

	 Neither can this PARALLEL be an asm.  We do not allow combining
	 that usually (see can_combine_p), so do not here either.  */
      bool ok = true;
      for (i = 0; ok && i < XVECLEN (p2, 0); i++)
	{
	  if ((GET_CODE (XVECEXP (p2, 0, i)) == SET
	       || GET_CODE (XVECEXP (p2, 0, i)) == CLOBBER
	       || GET_CODE (XVECEXP (p2, 0, i)) == CLOBBER_HIGH)
	      && reg_overlap_mentioned_p (SET_DEST (PATTERN (i3)),
					  SET_DEST (XVECEXP (p2, 0, i))))
	    ok = false;
	  else if (GET_CODE (XVECEXP (p2, 0, i)) == SET
		   && GET_CODE (SET_SRC (XVECEXP (p2, 0, i))) == ASM_OPERANDS)
	    ok = false;
	}

      if (ok)
	for (i = 0; i < XVECLEN (p2, 0); i++)
	  if (GET_CODE (XVECEXP (p2, 0, i)) == SET
	      && SET_DEST (XVECEXP (p2, 0, i)) == SET_SRC (PATTERN (i3)))
	    {
	      combine_merges++;

	      subst_insn = i3;
	      subst_low_luid = DF_INSN_LUID (i2);

	      added_sets_2 = added_sets_1 = added_sets_0 = 0;
	      i2src = SET_SRC (XVECEXP (p2, 0, i));
	      i2dest = SET_DEST (XVECEXP (p2, 0, i));
	      i2dest_killed = dead_or_set_p (i2, i2dest);

	      /* Replace the dest in I2 with our dest and make the resulting
		 insn the new pattern for I3.  Then skip to where we validate
		 the pattern.  Everything was set up above.  */
	      SUBST (SET_DEST (XVECEXP (p2, 0, i)), SET_DEST (PATTERN (i3)));
	      newpat = p2;
	      i3_subst_into_i2 = 1;
	      goto validate_replacement;
	    }
    }

  /* If I2 is setting a pseudo to a constant and I3 is setting some
     sub-part of it to another constant, merge them by making a new
     constant.  */
  if (i1 == 0
      && (temp_expr = single_set (i2)) != 0
      && is_a <scalar_int_mode> (GET_MODE (SET_DEST (temp_expr)), &temp_mode)
      && CONST_SCALAR_INT_P (SET_SRC (temp_expr))
      && GET_CODE (PATTERN (i3)) == SET
      && CONST_SCALAR_INT_P (SET_SRC (PATTERN (i3)))
      && reg_subword_p (SET_DEST (PATTERN (i3)), SET_DEST (temp_expr)))
    {
      rtx dest = SET_DEST (PATTERN (i3));
      rtx temp_dest = SET_DEST (temp_expr);
      int offset = -1;
      int width = 0;

      if (GET_CODE (dest) == ZERO_EXTRACT)
	{
	  if (CONST_INT_P (XEXP (dest, 1))
	      && CONST_INT_P (XEXP (dest, 2))
	      && is_a <scalar_int_mode> (GET_MODE (XEXP (dest, 0)),
					 &dest_mode))
	    {
	      width = INTVAL (XEXP (dest, 1));
	      offset = INTVAL (XEXP (dest, 2));
	      dest = XEXP (dest, 0);
	      if (BITS_BIG_ENDIAN)
		offset = GET_MODE_PRECISION (dest_mode) - width - offset;
	    }
	}
      else
	{
	  if (GET_CODE (dest) == STRICT_LOW_PART)
	    dest = XEXP (dest, 0);
	  if (is_a <scalar_int_mode> (GET_MODE (dest), &dest_mode))
	    {
	      width = GET_MODE_PRECISION (dest_mode);
	      offset = 0;
	    }
	}

      if (offset >= 0)
	{
	  /* If this is the low part, we're done.  */
	  if (subreg_lowpart_p (dest))
	    ;
	  /* Handle the case where inner is twice the size of outer.  */
	  else if (GET_MODE_PRECISION (temp_mode)
		   == 2 * GET_MODE_PRECISION (dest_mode))
	    offset += GET_MODE_PRECISION (dest_mode);
	  /* Otherwise give up for now.  */
	  else
	    offset = -1;
	}

      if (offset >= 0)
	{
	  rtx inner = SET_SRC (PATTERN (i3));
	  rtx outer = SET_SRC (temp_expr);

	  wide_int o = wi::insert (rtx_mode_t (outer, temp_mode),
				   rtx_mode_t (inner, dest_mode),
				   offset, width);

	  combine_merges++;
	  subst_insn = i3;
	  subst_low_luid = DF_INSN_LUID (i2);
	  added_sets_2 = added_sets_1 = added_sets_0 = 0;
	  i2dest = temp_dest;
	  i2dest_killed = dead_or_set_p (i2, i2dest);

	  /* Replace the source in I2 with the new constant and make the
	     resulting insn the new pattern for I3.  Then skip to where we
	     validate the pattern.  Everything was set up above.  */
	  SUBST (SET_SRC (temp_expr),
		 immed_wide_int_const (o, temp_mode));

	  newpat = PATTERN (i2);

          /* The dest of I3 has been replaced with the dest of I2.  */
          changed_i3_dest = 1;
	  goto validate_replacement;
	}
    }

  /* If we have no I1 and I2 looks like:
	(parallel [(set (reg:CC X) (compare:CC OP (const_int 0)))
		   (set Y OP)])
     make up a dummy I1 that is
	(set Y OP)
     and change I2 to be
	(set (reg:CC X) (compare:CC Y (const_int 0)))

     (We can ignore any trailing CLOBBERs.)

     This undoes a previous combination and allows us to match a branch-and-
     decrement insn.  */

  if (!HAVE_cc0 && i1 == 0
      && is_parallel_of_n_reg_sets (PATTERN (i2), 2)
      && (GET_MODE_CLASS (GET_MODE (SET_DEST (XVECEXP (PATTERN (i2), 0, 0))))
	  == MODE_CC)
      && GET_CODE (SET_SRC (XVECEXP (PATTERN (i2), 0, 0))) == COMPARE
      && XEXP (SET_SRC (XVECEXP (PATTERN (i2), 0, 0)), 1) == const0_rtx
      && rtx_equal_p (XEXP (SET_SRC (XVECEXP (PATTERN (i2), 0, 0)), 0),
		      SET_SRC (XVECEXP (PATTERN (i2), 0, 1)))
      && !reg_used_between_p (SET_DEST (XVECEXP (PATTERN (i2), 0, 0)), i2, i3)
      && !reg_used_between_p (SET_DEST (XVECEXP (PATTERN (i2), 0, 1)), i2, i3))
    {
      /* We make I1 with the same INSN_UID as I2.  This gives it
	 the same DF_INSN_LUID for value tracking.  Our fake I1 will
	 never appear in the insn stream so giving it the same INSN_UID
	 as I2 will not cause a problem.  */

      i1 = gen_rtx_INSN (VOIDmode, NULL, i2, BLOCK_FOR_INSN (i2),
			 XVECEXP (PATTERN (i2), 0, 1), INSN_LOCATION (i2),
			 -1, NULL_RTX);
      INSN_UID (i1) = INSN_UID (i2);

      SUBST (PATTERN (i2), XVECEXP (PATTERN (i2), 0, 0));
      SUBST (XEXP (SET_SRC (PATTERN (i2)), 0),
	     SET_DEST (PATTERN (i1)));
      unsigned int regno = REGNO (SET_DEST (PATTERN (i1)));
      SUBST_LINK (LOG_LINKS (i2),
		  alloc_insn_link (i1, regno, LOG_LINKS (i2)));
    }

  /* If I2 is a PARALLEL of two SETs of REGs (and perhaps some CLOBBERs),
     make those two SETs separate I1 and I2 insns, and make an I0 that is
     the original I1.  */
  if (!HAVE_cc0 && i0 == 0
      && is_parallel_of_n_reg_sets (PATTERN (i2), 2)
      && can_split_parallel_of_n_reg_sets (i2, 2)
      && !reg_used_between_p (SET_DEST (XVECEXP (PATTERN (i2), 0, 0)), i2, i3)
      && !reg_used_between_p (SET_DEST (XVECEXP (PATTERN (i2), 0, 1)), i2, i3)
      && !reg_set_between_p  (SET_DEST (XVECEXP (PATTERN (i2), 0, 0)), i2, i3)
      && !reg_set_between_p  (SET_DEST (XVECEXP (PATTERN (i2), 0, 1)), i2, i3))
    {
      /* If there is no I1, there is no I0 either.  */
      i0 = i1;

      /* We make I1 with the same INSN_UID as I2.  This gives it
	 the same DF_INSN_LUID for value tracking.  Our fake I1 will
	 never appear in the insn stream so giving it the same INSN_UID
	 as I2 will not cause a problem.  */

      i1 = gen_rtx_INSN (VOIDmode, NULL, i2, BLOCK_FOR_INSN (i2),
			 XVECEXP (PATTERN (i2), 0, 0), INSN_LOCATION (i2),
			 -1, NULL_RTX);
      INSN_UID (i1) = INSN_UID (i2);

      SUBST (PATTERN (i2), XVECEXP (PATTERN (i2), 0, 1));
    }

  /* Verify that I2 and maybe I1 and I0 can be combined into I3.  */
  if (!can_combine_p (i2, i3, i0, i1, NULL, NULL, &i2dest, &i2src))
    {
      if (dump_file)
	fprintf (dump_file, "Can't combine i2 into i3\n");
      undo_all ();
      return 0;
    }
  if (i1 && !can_combine_p (i1, i3, i0, NULL, i2, NULL, &i1dest, &i1src))
    {
      if (dump_file)
	fprintf (dump_file, "Can't combine i1 into i3\n");
      undo_all ();
      return 0;
    }
  if (i0 && !can_combine_p (i0, i3, NULL, NULL, i1, i2, &i0dest, &i0src))
    {
      if (dump_file)
	fprintf (dump_file, "Can't combine i0 into i3\n");
      undo_all ();
      return 0;
    }

  /* Record whether i2 and i3 are trivial moves.  */
  i2_was_move = is_just_move (i2);
  i3_was_move = is_just_move (i3);

  /* Record whether I2DEST is used in I2SRC and similarly for the other
     cases.  Knowing this will help in register status updating below.  */
  i2dest_in_i2src = reg_overlap_mentioned_p (i2dest, i2src);
  i1dest_in_i1src = i1 && reg_overlap_mentioned_p (i1dest, i1src);
  i2dest_in_i1src = i1 && reg_overlap_mentioned_p (i2dest, i1src);
  i0dest_in_i0src = i0 && reg_overlap_mentioned_p (i0dest, i0src);
  i1dest_in_i0src = i0 && reg_overlap_mentioned_p (i1dest, i0src);
  i2dest_in_i0src = i0 && reg_overlap_mentioned_p (i2dest, i0src);
  i2dest_killed = dead_or_set_p (i2, i2dest);
  i1dest_killed = i1 && dead_or_set_p (i1, i1dest);
  i0dest_killed = i0 && dead_or_set_p (i0, i0dest);

  /* For the earlier insns, determine which of the subsequent ones they
     feed.  */
  i1_feeds_i2_n = i1 && insn_a_feeds_b (i1, i2);
  i0_feeds_i1_n = i0 && insn_a_feeds_b (i0, i1);
  i0_feeds_i2_n = (i0 && (!i0_feeds_i1_n ? insn_a_feeds_b (i0, i2)
			  : (!reg_overlap_mentioned_p (i1dest, i0dest)
			     && reg_overlap_mentioned_p (i0dest, i2src))));

  /* Ensure that I3's pattern can be the destination of combines.  */
  if (! combinable_i3pat (i3, &PATTERN (i3), i2dest, i1dest, i0dest,
			  i1 && i2dest_in_i1src && !i1_feeds_i2_n,
			  i0 && ((i2dest_in_i0src && !i0_feeds_i2_n)
				 || (i1dest_in_i0src && !i0_feeds_i1_n)),
			  &i3dest_killed))
    {
      undo_all ();
      return 0;
    }

  /* See if any of the insns is a MULT operation.  Unless one is, we will
     reject a combination that is, since it must be slower.  Be conservative
     here.  */
  if (GET_CODE (i2src) == MULT
      || (i1 != 0 && GET_CODE (i1src) == MULT)
      || (i0 != 0 && GET_CODE (i0src) == MULT)
      || (GET_CODE (PATTERN (i3)) == SET
	  && GET_CODE (SET_SRC (PATTERN (i3))) == MULT))
    have_mult = 1;

  /* If I3 has an inc, then give up if I1 or I2 uses the reg that is inc'd.
     We used to do this EXCEPT in one case: I3 has a post-inc in an
     output operand.  However, that exception can give rise to insns like
	mov r3,(r3)+
     which is a famous insn on the PDP-11 where the value of r3 used as the
     source was model-dependent.  Avoid this sort of thing.  */

#if 0
  if (!(GET_CODE (PATTERN (i3)) == SET
	&& REG_P (SET_SRC (PATTERN (i3)))
	&& MEM_P (SET_DEST (PATTERN (i3)))
	&& (GET_CODE (XEXP (SET_DEST (PATTERN (i3)), 0)) == POST_INC
	    || GET_CODE (XEXP (SET_DEST (PATTERN (i3)), 0)) == POST_DEC)))
    /* It's not the exception.  */
#endif
    if (AUTO_INC_DEC)
      {
	rtx link;
	for (link = REG_NOTES (i3); link; link = XEXP (link, 1))
	  if (REG_NOTE_KIND (link) == REG_INC
	      && (reg_overlap_mentioned_p (XEXP (link, 0), PATTERN (i2))
		  || (i1 != 0
		      && reg_overlap_mentioned_p (XEXP (link, 0), PATTERN (i1)))))
	    {
	      undo_all ();
	      return 0;
	    }
      }

  /* See if the SETs in I1 or I2 need to be kept around in the merged
     instruction: whenever the value set there is still needed past I3.
     For the SET in I2, this is easy: we see if I2DEST dies or is set in I3.

     For the SET in I1, we have two cases: if I1 and I2 independently feed
     into I3, the set in I1 needs to be kept around unless I1DEST dies
     or is set in I3.  Otherwise (if I1 feeds I2 which feeds I3), the set
     in I1 needs to be kept around unless I1DEST dies or is set in either
     I2 or I3.  The same considerations apply to I0.  */

  added_sets_2 = !dead_or_set_p (i3, i2dest);

  if (i1)
    added_sets_1 = !(dead_or_set_p (i3, i1dest)
		     || (i1_feeds_i2_n && dead_or_set_p (i2, i1dest)));
  else
    added_sets_1 = 0;

  if (i0)
    added_sets_0 =  !(dead_or_set_p (i3, i0dest)
		      || (i0_feeds_i1_n && dead_or_set_p (i1, i0dest))
		      || ((i0_feeds_i2_n || (i0_feeds_i1_n && i1_feeds_i2_n))
			  && dead_or_set_p (i2, i0dest)));
  else
    added_sets_0 = 0;

  /* We are about to copy insns for the case where they need to be kept
     around.  Check that they can be copied in the merged instruction.  */

  if (targetm.cannot_copy_insn_p
      && ((added_sets_2 && targetm.cannot_copy_insn_p (i2))
	  || (i1 && added_sets_1 && targetm.cannot_copy_insn_p (i1))
	  || (i0 && added_sets_0 && targetm.cannot_copy_insn_p (i0))))
    {
      undo_all ();
      return 0;
    }

  /* If the set in I2 needs to be kept around, we must make a copy of
     PATTERN (I2), so that when we substitute I1SRC for I1DEST in
     PATTERN (I2), we are only substituting for the original I1DEST, not into
     an already-substituted copy.  This also prevents making self-referential
     rtx.  If I2 is a PARALLEL, we just need the piece that assigns I2SRC to
     I2DEST.  */

  if (added_sets_2)
    {
      if (GET_CODE (PATTERN (i2)) == PARALLEL)
	i2pat = gen_rtx_SET (i2dest, copy_rtx (i2src));
      else
	i2pat = copy_rtx (PATTERN (i2));
    }

  if (added_sets_1)
    {
      if (GET_CODE (PATTERN (i1)) == PARALLEL)
	i1pat = gen_rtx_SET (i1dest, copy_rtx (i1src));
      else
	i1pat = copy_rtx (PATTERN (i1));
    }

  if (added_sets_0)
    {
      if (GET_CODE (PATTERN (i0)) == PARALLEL)
	i0pat = gen_rtx_SET (i0dest, copy_rtx (i0src));
      else
	i0pat = copy_rtx (PATTERN (i0));
    }

  combine_merges++;

  /* Substitute in the latest insn for the regs set by the earlier ones.  */

  maxreg = max_reg_num ();

  subst_insn = i3;

  /* Many machines that don't use CC0 have insns that can both perform an
     arithmetic operation and set the condition code.  These operations will
     be represented as a PARALLEL with the first element of the vector
     being a COMPARE of an arithmetic operation with the constant zero.
     The second element of the vector will set some pseudo to the result
     of the same arithmetic operation.  If we simplify the COMPARE, we won't
     match such a pattern and so will generate an extra insn.   Here we test
     for this case, where both the comparison and the operation result are
     needed, and make the PARALLEL by just replacing I2DEST in I3SRC with
     I2SRC.  Later we will make the PARALLEL that contains I2.  */

  if (!HAVE_cc0 && i1 == 0 && added_sets_2 && GET_CODE (PATTERN (i3)) == SET
      && GET_CODE (SET_SRC (PATTERN (i3))) == COMPARE
      && CONST_INT_P (XEXP (SET_SRC (PATTERN (i3)), 1))
      && rtx_equal_p (XEXP (SET_SRC (PATTERN (i3)), 0), i2dest))
    {
      rtx newpat_dest;
      rtx *cc_use_loc = NULL;
      rtx_insn *cc_use_insn = NULL;
      rtx op0 = i2src, op1 = XEXP (SET_SRC (PATTERN (i3)), 1);
      machine_mode compare_mode, orig_compare_mode;
      enum rtx_code compare_code = UNKNOWN, orig_compare_code = UNKNOWN;
      scalar_int_mode mode;

      newpat = PATTERN (i3);
      newpat_dest = SET_DEST (newpat);
      compare_mode = orig_compare_mode = GET_MODE (newpat_dest);

      if (undobuf.other_insn == 0
	  && (cc_use_loc = find_single_use (SET_DEST (newpat), i3,
					    &cc_use_insn)))
	{
	  compare_code = orig_compare_code = GET_CODE (*cc_use_loc);
	  if (is_a <scalar_int_mode> (GET_MODE (i2dest), &mode))
	    compare_code = simplify_compare_const (compare_code, mode,
						   op0, &op1);
	  target_canonicalize_comparison (&compare_code, &op0, &op1, 1);
	}

      /* Do the rest only if op1 is const0_rtx, which may be the
	 result of simplification.  */
      if (op1 == const0_rtx)
	{
	  /* If a single use of the CC is found, prepare to modify it
	     when SELECT_CC_MODE returns a new CC-class mode, or when
	     the above simplify_compare_const() returned a new comparison
	     operator.  undobuf.other_insn is assigned the CC use insn
	     when modifying it.  */
	  if (cc_use_loc)
	    {
#ifdef SELECT_CC_MODE
	      machine_mode new_mode
		= SELECT_CC_MODE (compare_code, op0, op1);
	      if (new_mode != orig_compare_mode
		  && can_change_dest_mode (SET_DEST (newpat),
					   added_sets_2, new_mode))
		{
		  unsigned int regno = REGNO (newpat_dest);
		  compare_mode = new_mode;
		  if (regno < FIRST_PSEUDO_REGISTER)
		    newpat_dest = gen_rtx_REG (compare_mode, regno);
		  else
		    {
		      SUBST_MODE (regno_reg_rtx[regno], compare_mode);
		      newpat_dest = regno_reg_rtx[regno];
		    }
		}
#endif
	      /* Cases for modifying the CC-using comparison.  */
	      if (compare_code != orig_compare_code
		  /* ??? Do we need to verify the zero rtx?  */
		  && XEXP (*cc_use_loc, 1) == const0_rtx)
		{
		  /* Replace cc_use_loc with entire new RTX.  */
		  SUBST (*cc_use_loc,
			 gen_rtx_fmt_ee (compare_code, GET_MODE (*cc_use_loc),
					 newpat_dest, const0_rtx));
		  undobuf.other_insn = cc_use_insn;
		}
	      else if (compare_mode != orig_compare_mode)
		{
		  /* Just replace the CC reg with a new mode.  */
		  SUBST (XEXP (*cc_use_loc, 0), newpat_dest);
		  undobuf.other_insn = cc_use_insn;
		}
	    }

	  /* Now we modify the current newpat:
	     First, SET_DEST(newpat) is updated if the CC mode has been
	     altered. For targets without SELECT_CC_MODE, this should be
	     optimized away.  */
	  if (compare_mode != orig_compare_mode)
	    SUBST (SET_DEST (newpat), newpat_dest);
	  /* This is always done to propagate i2src into newpat.  */
	  SUBST (SET_SRC (newpat),
		 gen_rtx_COMPARE (compare_mode, op0, op1));
	  /* Create new version of i2pat if needed; the below PARALLEL
	     creation needs this to work correctly.  */
	  if (! rtx_equal_p (i2src, op0))
	    i2pat = gen_rtx_SET (i2dest, op0);
	  i2_is_used = 1;
	}
    }

  if (i2_is_used == 0)
    {
      /* It is possible that the source of I2 or I1 may be performing
	 an unneeded operation, such as a ZERO_EXTEND of something
	 that is known to have the high part zero.  Handle that case
	 by letting subst look at the inner insns.

	 Another way to do this would be to have a function that tries
	 to simplify a single insn instead of merging two or more
	 insns.  We don't do this because of the potential of infinite
	 loops and because of the potential extra memory required.
	 However, doing it the way we are is a bit of a kludge and
	 doesn't catch all cases.

	 But only do this if -fexpensive-optimizations since it slows
	 things down and doesn't usually win.

	 This is not done in the COMPARE case above because the
	 unmodified I2PAT is used in the PARALLEL and so a pattern
	 with a modified I2SRC would not match.  */

      if (flag_expensive_optimizations)
	{
	  /* Pass pc_rtx so no substitutions are done, just
	     simplifications.  */
	  if (i1)
	    {
	      subst_low_luid = DF_INSN_LUID (i1);
	      i1src = subst (i1src, pc_rtx, pc_rtx, 0, 0, 0);
	    }

	  subst_low_luid = DF_INSN_LUID (i2);
	  i2src = subst (i2src, pc_rtx, pc_rtx, 0, 0, 0);
	}

      n_occurrences = 0;		/* `subst' counts here */
      subst_low_luid = DF_INSN_LUID (i2);

      /* If I1 feeds into I2 and I1DEST is in I1SRC, we need to make a unique
	 copy of I2SRC each time we substitute it, in order to avoid creating
	 self-referential RTL when we will be substituting I1SRC for I1DEST
	 later.  Likewise if I0 feeds into I2, either directly or indirectly
	 through I1, and I0DEST is in I0SRC.  */
      newpat = subst (PATTERN (i3), i2dest, i2src, 0, 0,
		      (i1_feeds_i2_n && i1dest_in_i1src)
		      || ((i0_feeds_i2_n || (i0_feeds_i1_n && i1_feeds_i2_n))
			  && i0dest_in_i0src));
      substed_i2 = 1;

      /* Record whether I2's body now appears within I3's body.  */
      i2_is_used = n_occurrences;
    }

  /* If we already got a failure, don't try to do more.  Otherwise, try to
     substitute I1 if we have it.  */

  if (i1 && GET_CODE (newpat) != CLOBBER)
    {
      /* Check that an autoincrement side-effect on I1 has not been lost.
	 This happens if I1DEST is mentioned in I2 and dies there, and
	 has disappeared from the new pattern.  */
      if ((FIND_REG_INC_NOTE (i1, NULL_RTX) != 0
	   && i1_feeds_i2_n
	   && dead_or_set_p (i2, i1dest)
	   && !reg_overlap_mentioned_p (i1dest, newpat))
	   /* Before we can do this substitution, we must redo the test done
	      above (see detailed comments there) that ensures I1DEST isn't
	      mentioned in any SETs in NEWPAT that are field assignments.  */
	  || !combinable_i3pat (NULL, &newpat, i1dest, NULL_RTX, NULL_RTX,
				0, 0, 0))
	{
	  undo_all ();
	  return 0;
	}

      n_occurrences = 0;
      subst_low_luid = DF_INSN_LUID (i1);

      /* If the following substitution will modify I1SRC, make a copy of it
	 for the case where it is substituted for I1DEST in I2PAT later.  */
      if (added_sets_2 && i1_feeds_i2_n)
	i1src_copy = copy_rtx (i1src);

      /* If I0 feeds into I1 and I0DEST is in I0SRC, we need to make a unique
	 copy of I1SRC each time we substitute it, in order to avoid creating
	 self-referential RTL when we will be substituting I0SRC for I0DEST
	 later.  */
      newpat = subst (newpat, i1dest, i1src, 0, 0,
		      i0_feeds_i1_n && i0dest_in_i0src);
      substed_i1 = 1;

      /* Record whether I1's body now appears within I3's body.  */
      i1_is_used = n_occurrences;
    }

  /* Likewise for I0 if we have it.  */

  if (i0 && GET_CODE (newpat) != CLOBBER)
    {
      if ((FIND_REG_INC_NOTE (i0, NULL_RTX) != 0
	   && ((i0_feeds_i2_n && dead_or_set_p (i2, i0dest))
	       || (i0_feeds_i1_n && dead_or_set_p (i1, i0dest)))
	   && !reg_overlap_mentioned_p (i0dest, newpat))
	  || !combinable_i3pat (NULL, &newpat, i0dest, NULL_RTX, NULL_RTX,
				0, 0, 0))
	{
	  undo_all ();
	  return 0;
	}

      /* If the following substitution will modify I0SRC, make a copy of it
	 for the case where it is substituted for I0DEST in I1PAT later.  */
      if (added_sets_1 && i0_feeds_i1_n)
	i0src_copy = copy_rtx (i0src);
      /* And a copy for I0DEST in I2PAT substitution.  */
      if (added_sets_2 && ((i0_feeds_i1_n && i1_feeds_i2_n)
			   || (i0_feeds_i2_n)))
	i0src_copy2 = copy_rtx (i0src);

      n_occurrences = 0;
      subst_low_luid = DF_INSN_LUID (i0);
      newpat = subst (newpat, i0dest, i0src, 0, 0, 0);
      substed_i0 = 1;
    }

  /* Fail if an autoincrement side-effect has been duplicated.  Be careful
     to count all the ways that I2SRC and I1SRC can be used.  */
  if ((FIND_REG_INC_NOTE (i2, NULL_RTX) != 0
       && i2_is_used + added_sets_2 > 1)
      || (i1 != 0 && FIND_REG_INC_NOTE (i1, NULL_RTX) != 0
	  && (i1_is_used + added_sets_1 + (added_sets_2 && i1_feeds_i2_n)
	      > 1))
      || (i0 != 0 && FIND_REG_INC_NOTE (i0, NULL_RTX) != 0
	  && (n_occurrences + added_sets_0
	      + (added_sets_1 && i0_feeds_i1_n)
	      + (added_sets_2 && i0_feeds_i2_n)
	      > 1))
      /* Fail if we tried to make a new register.  */
      || max_reg_num () != maxreg
      /* Fail if we couldn't do something and have a CLOBBER.  */
      || GET_CODE (newpat) == CLOBBER
      /* Fail if this new pattern is a MULT and we didn't have one before
	 at the outer level.  */
      || (GET_CODE (newpat) == SET && GET_CODE (SET_SRC (newpat)) == MULT
	  && ! have_mult))
    {
      undo_all ();
      return 0;
    }

  /* If the actions of the earlier insns must be kept
     in addition to substituting them into the latest one,
     we must make a new PARALLEL for the latest insn
     to hold additional the SETs.  */

  if (added_sets_0 || added_sets_1 || added_sets_2)
    {
      int extra_sets = added_sets_0 + added_sets_1 + added_sets_2;
      combine_extras++;

      if (GET_CODE (newpat) == PARALLEL)
	{
	  rtvec old = XVEC (newpat, 0);
	  total_sets = XVECLEN (newpat, 0) + extra_sets;
	  newpat = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (total_sets));
	  memcpy (XVEC (newpat, 0)->elem, &old->elem[0],
		  sizeof (old->elem[0]) * old->num_elem);
	}
      else
	{
	  rtx old = newpat;
	  total_sets = 1 + extra_sets;
	  newpat = gen_rtx_PARALLEL (VOIDmode, rtvec_alloc (total_sets));
	  XVECEXP (newpat, 0, 0) = old;
	}

      if (added_sets_0)
	XVECEXP (newpat, 0, --total_sets) = i0pat;

      if (added_sets_1)
	{
	  rtx t = i1pat;
	  if (i0_feeds_i1_n)
	    t = subst (t, i0dest, i0src_copy ? i0src_copy : i0src, 0, 0, 0);

	  XVECEXP (newpat, 0, --total_sets) = t;
	}
      if (added_sets_2)
	{
	  rtx t = i2pat;
	  if (i1_feeds_i2_n)
	    t = subst (t, i1dest, i1src_copy ? i1src_copy : i1src, 0, 0,
		       i0_feeds_i1_n && i0dest_in_i0src);
	  if ((i0_feeds_i1_n && i1_feeds_i2_n) || i0_feeds_i2_n)
	    t = subst (t, i0dest, i0src_copy2 ? i0src_copy2 : i0src, 0, 0, 0);

	  XVECEXP (newpat, 0, --total_sets) = t;
	}
    }

 validate_replacement:

  /* Note which hard regs this insn has as inputs.  */
  mark_used_regs_combine (newpat);

  /* If recog_for_combine fails, it strips existing clobbers.  If we'll
     consider splitting this pattern, we might need these clobbers.  */
  if (i1 && GET_CODE (newpat) == PARALLEL
      && GET_CODE (XVECEXP (newpat, 0, XVECLEN (newpat, 0) - 1)) == CLOBBER)
    {
      int len = XVECLEN (newpat, 0);

      newpat_vec_with_clobbers = rtvec_alloc (len);
      for (i = 0; i < len; i++)
	RTVEC_ELT (newpat_vec_with_clobbers, i) = XVECEXP (newpat, 0, i);
    }

  /* We have recognized nothing yet.  */
  insn_code_number = -1;

  /* See if this is a PARALLEL of two SETs where one SET's destination is
     a register that is unused and this isn't marked as an instruction that
     might trap in an EH region.  In that case, we just need the other SET.
     We prefer this over the PARALLEL.

     This can occur when simplifying a divmod insn.  We *must* test for this
     case here because the code below that splits two independent SETs doesn't
     handle this case correctly when it updates the register status.

     It's pointless doing this if we originally had two sets, one from
     i3, and one from i2.  Combining then splitting the parallel results
     in the original i2 again plus an invalid insn (which we delete).
     The net effect is only to move instructions around, which makes
     debug info less accurate.

     If the remaining SET came from I2 its destination should not be used
     between I2 and I3.  See PR82024.  */

  if (!(added_sets_2 && i1 == 0)
      && is_parallel_of_n_reg_sets (newpat, 2)
      && asm_noperands (newpat) < 0)
    {
      rtx set0 = XVECEXP (newpat, 0, 0);
      rtx set1 = XVECEXP (newpat, 0, 1);
      rtx oldpat = newpat;

      if (((REG_P (SET_DEST (set1))
	    && find_reg_note (i3, REG_UNUSED, SET_DEST (set1)))
	   || (GET_CODE (SET_DEST (set1)) == SUBREG
	       && find_reg_note (i3, REG_UNUSED, SUBREG_REG (SET_DEST (set1)))))
	  && insn_nothrow_p (i3)
	  && !side_effects_p (SET_SRC (set1)))
	{
	  newpat = set0;
	  insn_code_number = recog_for_combine (&newpat, i3, &new_i3_notes);
	}

      else if (((REG_P (SET_DEST (set0))
		 && find_reg_note (i3, REG_UNUSED, SET_DEST (set0)))
		|| (GET_CODE (SET_DEST (set0)) == SUBREG
		    && find_reg_note (i3, REG_UNUSED,
				      SUBREG_REG (SET_DEST (set0)))))
	       && insn_nothrow_p (i3)
	       && !side_effects_p (SET_SRC (set0)))
	{
	  rtx dest = SET_DEST (set1);
	  if (GET_CODE (dest) == SUBREG)
	    dest = SUBREG_REG (dest);
	  if (!reg_used_between_p (dest, i2, i3))
	    {
	      newpat = set1;
	      insn_code_number = recog_for_combine (&newpat, i3, &new_i3_notes);

	      if (insn_code_number >= 0)
		changed_i3_dest = 1;
	    }
	}

      if (insn_code_number < 0)
	newpat = oldpat;
    }

  /* Is the result of combination a valid instruction?  */
  if (insn_code_number < 0)
    insn_code_number = recog_for_combine (&newpat, i3, &new_i3_notes);

  /* If we were combining three insns and the result is a simple SET
     with no ASM_OPERANDS that wasn't recognized, try to split it into two
     insns.  There are two ways to do this.  It can be split using a
     machine-specific method (like when you have an addition of a large
     constant) or by combine in the function find_split_point.  */

  if (i1 && insn_code_number < 0 && GET_CODE (newpat) == SET
      && asm_noperands (newpat) < 0)
    {
      rtx parallel, *split;
      rtx_insn *m_split_insn;

      /* See if the MD file can split NEWPAT.  If it can't, see if letting it
	 use I2DEST as a scratch register will help.  In the latter case,
	 convert I2DEST to the mode of the source of NEWPAT if we can.  */

      m_split_insn = combine_split_insns (newpat, i3);

      /* We can only use I2DEST as a scratch reg if it doesn't overlap any
	 inputs of NEWPAT.  */

      /* ??? If I2DEST is not safe, and I1DEST exists, then it would be
	 possible to try that as a scratch reg.  This would require adding
	 more code to make it work though.  */

      if (m_split_insn == 0 && ! reg_overlap_mentioned_p (i2dest, newpat))
	{
	  machine_mode new_mode = GET_MODE (SET_DEST (newpat));

	  /* ??? Reusing i2dest without resetting the reg_stat entry for it
	     (temporarily, until we are committed to this instruction
	     combination) does not work: for example, any call to nonzero_bits
	     on the register (from a splitter in the MD file, for example)
	     will get the old information, which is invalid.

	     Since nowadays we can create registers during combine just fine,
	     we should just create a new one here, not reuse i2dest.  */

	  /* First try to split using the original register as a
	     scratch register.  */
	  parallel = gen_rtx_PARALLEL (VOIDmode,
				       gen_rtvec (2, newpat,
						  gen_rtx_CLOBBER (VOIDmode,
								   i2dest)));
	  m_split_insn = combine_split_insns (parallel, i3);

	  /* If that didn't work, try changing the mode of I2DEST if
	     we can.  */
	  if (m_split_insn == 0
	      && new_mode != GET_MODE (i2dest)
	      && new_mode != VOIDmode
	      && can_change_dest_mode (i2dest, added_sets_2, new_mode))
	    {
	      machine_mode old_mode = GET_MODE (i2dest);
	      rtx ni2dest;

	      if (REGNO (i2dest) < FIRST_PSEUDO_REGISTER)
		ni2dest = gen_rtx_REG (new_mode, REGNO (i2dest));
	      else
		{
		  SUBST_MODE (regno_reg_rtx[REGNO (i2dest)], new_mode);
		  ni2dest = regno_reg_rtx[REGNO (i2dest)];
		}

	      parallel = (gen_rtx_PARALLEL
			  (VOIDmode,
			   gen_rtvec (2, newpat,
				      gen_rtx_CLOBBER (VOIDmode,
						       ni2dest))));
	      m_split_insn = combine_split_insns (parallel, i3);

	      if (m_split_insn == 0
		  && REGNO (i2dest) >= FIRST_PSEUDO_REGISTER)
		{
		  struct undo *buf;

		  adjust_reg_mode (regno_reg_rtx[REGNO (i2dest)], old_mode);
		  buf = undobuf.undos;
		  undobuf.undos = buf->next;
		  buf->next = undobuf.frees;
		  undobuf.frees = buf;
		}
	    }

	  i2scratch = m_split_insn != 0;
	}

      /* If recog_for_combine has discarded clobbers, try to use them
	 again for the split.  */
      if (m_split_insn == 0 && newpat_vec_with_clobbers)
	{
	  parallel = gen_rtx_PARALLEL (VOIDmode, newpat_vec_with_clobbers);
	  m_split_insn = combine_split_insns (parallel, i3);
	}

      if (m_split_insn && NEXT_INSN (m_split_insn) == NULL_RTX)
	{
	  rtx m_split_pat = PATTERN (m_split_insn);
	  insn_code_number = recog_for_combine (&m_split_pat, i3, &new_i3_notes);
	  if (insn_code_number >= 0)
	    newpat = m_split_pat;
	}
      else if (m_split_insn && NEXT_INSN (NEXT_INSN (m_split_insn)) == NULL_RTX
	       && (next_nonnote_nondebug_insn (i2) == i3
		   || !modified_between_p (PATTERN (m_split_insn), i2, i3)))
	{
	  rtx i2set, i3set;
	  rtx newi3pat = PATTERN (NEXT_INSN (m_split_insn));
	  newi2pat = PATTERN (m_split_insn);

	  i3set = single_set (NEXT_INSN (m_split_insn));
	  i2set = single_set (m_split_insn);

	  i2_code_number = recog_for_combine (&newi2pat, i2, &new_i2_notes);

	  /* If I2 or I3 has multiple SETs, we won't know how to track
	     register status, so don't use these insns.  If I2's destination
	     is used between I2 and I3, we also can't use these insns.  */

	  if (i2_code_number >= 0 && i2set && i3set
	      && (next_nonnote_nondebug_insn (i2) == i3
		  || ! reg_used_between_p (SET_DEST (i2set), i2, i3)))
	    insn_code_number = recog_for_combine (&newi3pat, i3,
						  &new_i3_notes);
	  if (insn_code_number >= 0)
	    newpat = newi3pat;

	  /* It is possible that both insns now set the destination of I3.
	     If so, we must show an extra use of it.  */

	  if (insn_code_number >= 0)
	    {
	      rtx new_i3_dest = SET_DEST (i3set);
	      rtx new_i2_dest = SET_DEST (i2set);

	      while (GET_CODE (new_i3_dest) == ZERO_EXTRACT
		     || GET_CODE (new_i3_dest) == STRICT_LOW_PART
		     || GET_CODE (new_i3_dest) == SUBREG)
		new_i3_dest = XEXP (new_i3_dest, 0);

	      while (GET_CODE (new_i2_dest) == ZERO_EXTRACT
		     || GET_CODE (new_i2_dest) == STRICT_LOW_PART
		     || GET_CODE (new_i2_dest) == SUBREG)
		new_i2_dest = XEXP (new_i2_dest, 0);

	      if (REG_P (new_i3_dest)
		  && REG_P (new_i2_dest)
		  && REGNO (new_i3_dest) == REGNO (new_i2_dest)
		  && REGNO (new_i2_dest) < reg_n_sets_max)
		INC_REG_N_SETS (REGNO (new_i2_dest), 1);
	    }
	}

      /* If we can split it and use I2DEST, go ahead and see if that
	 helps things be recognized.  Verify that none of the registers
	 are set between I2 and I3.  */
      if (insn_code_number < 0
          && (split = find_split_point (&newpat, i3, false)) != 0
	  && (!HAVE_cc0 || REG_P (i2dest))
	  /* We need I2DEST in the proper mode.  If it is a hard register
	     or the only use of a pseudo, we can change its mode.
	     Make sure we don't change a hard register to have a mode that
	     isn't valid for it, or change the number of registers.  */
	  && (GET_MODE (*split) == GET_MODE (i2dest)
	      || GET_MODE (*split) == VOIDmode
	      || can_change_dest_mode (i2dest, added_sets_2,
				       GET_MODE (*split)))
	  && (next_nonnote_nondebug_insn (i2) == i3
	      || !modified_between_p (*split, i2, i3))
	  /* We can't overwrite I2DEST if its value is still used by
	     NEWPAT.  */
	  && ! reg_referenced_p (i2dest, newpat))
	{
	  rtx newdest = i2dest;
	  enum rtx_code split_code = GET_CODE (*split);
	  machine_mode split_mode = GET_MODE (*split);
	  bool subst_done = false;
	  newi2pat = NULL_RTX;

	  i2scratch = true;

	  /* *SPLIT may be part of I2SRC, so make sure we have the
	     original expression around for later debug processing.
	     We should not need I2SRC any more in other cases.  */
	  if (MAY_HAVE_DEBUG_BIND_INSNS)
	    i2src = copy_rtx (i2src);
	  else
	    i2src = NULL;

	  /* Get NEWDEST as a register in the proper mode.  We have already
	     validated that we can do this.  */
	  if (GET_MODE (i2dest) != split_mode && split_mode != VOIDmode)
	    {
	      if (REGNO (i2dest) < FIRST_PSEUDO_REGISTER)
		newdest = gen_rtx_REG (split_mode, REGNO (i2dest));
	      else
		{
		  SUBST_MODE (regno_reg_rtx[REGNO (i2dest)], split_mode);
		  newdest = regno_reg_rtx[REGNO (i2dest)];
		}
	    }

	  /* If *SPLIT is a (mult FOO (const_int pow2)), convert it to
	     an ASHIFT.  This can occur if it was inside a PLUS and hence
	     appeared to be a memory address.  This is a kludge.  */
	  if (split_code == MULT
	      && CONST_INT_P (XEXP (*split, 1))
	      && INTVAL (XEXP (*split, 1)) > 0
	      && (i = exact_log2 (UINTVAL (XEXP (*split, 1)))) >= 0)
	    {
	      rtx i_rtx = gen_int_shift_amount (split_mode, i);
	      SUBST (*split, gen_rtx_ASHIFT (split_mode,
					     XEXP (*split, 0), i_rtx));
	      /* Update split_code because we may not have a multiply
		 anymore.  */
	      split_code = GET_CODE (*split);
	    }

	  /* Similarly for (plus (mult FOO (const_int pow2))).  */
	  if (split_code == PLUS
	      && GET_CODE (XEXP (*split, 0)) == MULT
	      && CONST_INT_P (XEXP (XEXP (*split, 0), 1))
	      && INTVAL (XEXP (XEXP (*split, 0), 1)) > 0
	      && (i = exact_log2 (UINTVAL (XEXP (XEXP (*split, 0), 1)))) >= 0)
	    {
	      rtx nsplit = XEXP (*split, 0);
	      rtx i_rtx = gen_int_shift_amount (GET_MODE (nsplit), i);
	      SUBST (XEXP (*split, 0), gen_rtx_ASHIFT (GET_MODE (nsplit),
						       XEXP (nsplit, 0),
						       i_rtx));
	      /* Update split_code because we may not have a multiply
		 anymore.  */
	      split_code = GET_CODE (*split);
	    }

#ifdef INSN_SCHEDULING
	  /* If *SPLIT is a paradoxical SUBREG, when we split it, it should
	     be written as a ZERO_EXTEND.  */
	  if (split_code == SUBREG && MEM_P (SUBREG_REG (*split)))
	    {
	      /* Or as a SIGN_EXTEND if LOAD_EXTEND_OP says that that's
		 what it really is.  */
	      if (load_extend_op (GET_MODE (SUBREG_REG (*split)))
		  == SIGN_EXTEND)
		SUBST (*split, gen_rtx_SIGN_EXTEND (split_mode,
						    SUBREG_REG (*split)));
	      else
		SUBST (*split, gen_rtx_ZERO_EXTEND (split_mode,
						    SUBREG_REG (*split)));
	    }
#endif

	  /* Attempt to split binary operators using arithmetic identities.  */
	  if (BINARY_P (SET_SRC (newpat))
	      && split_mode == GET_MODE (SET_SRC (newpat))
	      && ! side_effects_p (SET_SRC (newpat)))
	    {
	      rtx setsrc = SET_SRC (newpat);
	      machine_mode mode = GET_MODE (setsrc);
	      enum rtx_code code = GET_CODE (setsrc);
	      rtx src_op0 = XEXP (setsrc, 0);
	      rtx src_op1 = XEXP (setsrc, 1);

	      /* Split "X = Y op Y" as "Z = Y; X = Z op Z".  */
	      if (rtx_equal_p (src_op0, src_op1))
		{
		  newi2pat = gen_rtx_SET (newdest, src_op0);
		  SUBST (XEXP (setsrc, 0), newdest);
		  SUBST (XEXP (setsrc, 1), newdest);
		  subst_done = true;
		}
	      /* Split "((P op Q) op R) op S" where op is PLUS or MULT.  */
	      else if ((code == PLUS || code == MULT)
		       && GET_CODE (src_op0) == code
		       && GET_CODE (XEXP (src_op0, 0)) == code
		       && (INTEGRAL_MODE_P (mode)
			   || (FLOAT_MODE_P (mode)
			       && flag_unsafe_math_optimizations)))
		{
		  rtx p = XEXP (XEXP (src_op0, 0), 0);
		  rtx q = XEXP (XEXP (src_op0, 0), 1);
		  rtx r = XEXP (src_op0, 1);
		  rtx s = src_op1;

		  /* Split both "((X op Y) op X) op Y" and
		     "((X op Y) op Y) op X" as "T op T" where T is
		     "X op Y".  */
		  if ((rtx_equal_p (p,r) && rtx_equal_p (q,s))
		       || (rtx_equal_p (p,s) && rtx_equal_p (q,r)))
		    {
		      newi2pat = gen_rtx_SET (newdest, XEXP (src_op0, 0));
		      SUBST (XEXP (setsrc, 0), newdest);
		      SUBST (XEXP (setsrc, 1), newdest);
		      subst_done = true;
		    }
		  /* Split "((X op X) op Y) op Y)" as "T op T" where
		     T is "X op Y".  */
		  else if (rtx_equal_p (p,q) && rtx_equal_p (r,s))
		    {
		      rtx tmp = simplify_gen_binary (code, mode, p, r);
		      newi2pat = gen_rtx_SET (newdest, tmp);
		      SUBST (XEXP (setsrc, 0), newdest);
		      SUBST (XEXP (setsrc, 1), newdest);
		      subst_done = true;
		    }
		}
	    }

	  if (!subst_done)
	    {
	      newi2pat = gen_rtx_SET (newdest, *split);
	      SUBST (*split, newdest);
	    }

	  i2_code_number = recog_for_combine (&newi2pat, i2, &new_i2_notes);

	  /* recog_for_combine might have added CLOBBERs to newi2pat.
	     Make sure NEWPAT does not depend on the clobbered regs.  */
	  if (GET_CODE (newi2pat) == PARALLEL)
	    for (i = XVECLEN (newi2pat, 0) - 1; i >= 0; i--)
	      if (GET_CODE (XVECEXP (newi2pat, 0, i)) == CLOBBER)
		{
		  rtx reg = XEXP (XVECEXP (newi2pat, 0, i), 0);
		  if (reg_overlap_mentioned_p (reg, newpat))
		    {
		      undo_all ();
		      return 0;
		    }
		}

	  /* If the split point was a MULT and we didn't have one before,
	     don't use one now.  */
	  if (i2_code_number >= 0 && ! (split_code == MULT && ! have_mult))
	    insn_code_number = recog_for_combine (&newpat, i3, &new_i3_notes);
	}
    }

  /* Check for a case where we loaded from memory in a narrow mode and
     then sign extended it, but we need both registers.  In that case,
     we have a PARALLEL with both loads from the same memory location.
     We can split this into a load from memory followed by a register-register
     copy.  This saves at least one insn, more if register allocation can
     eliminate the copy.

     We cannot do this if the destination of the first assignment is a
     condition code register or cc0.  We eliminate this case by making sure
     the SET_DEST and SET_SRC have the same mode.

     We cannot do this if the destination of the second assignment is
     a register that we have already assumed is zero-extended.  Similarly
     for a SUBREG of such a register.  */

  else if (i1 && insn_code_number < 0 && asm_noperands (newpat) < 0
	   && GET_CODE (newpat) == PARALLEL
	   && XVECLEN (newpat, 0) == 2
	   && GET_CODE (XVECEXP (newpat, 0, 0)) == SET
	   && GET_CODE (SET_SRC (XVECEXP (newpat, 0, 0))) == SIGN_EXTEND
	   && (GET_MODE (SET_DEST (XVECEXP (newpat, 0, 0)))
	       == GET_MODE (SET_SRC (XVECEXP (newpat, 0, 0))))
	   && GET_CODE (XVECEXP (newpat, 0, 1)) == SET
	   && rtx_equal_p (SET_SRC (XVECEXP (newpat, 0, 1)),
			   XEXP (SET_SRC (XVECEXP (newpat, 0, 0)), 0))
	   && !modified_between_p (SET_SRC (XVECEXP (newpat, 0, 1)), i2, i3)
	   && GET_CODE (SET_DEST (XVECEXP (newpat, 0, 1))) != ZERO_EXTRACT
	   && GET_CODE (SET_DEST (XVECEXP (newpat, 0, 1))) != STRICT_LOW_PART
	   && ! (temp_expr = SET_DEST (XVECEXP (newpat, 0, 1)),
		 (REG_P (temp_expr)
		  && reg_stat[REGNO (temp_expr)].nonzero_bits != 0
		  && known_lt (GET_MODE_PRECISION (GET_MODE (temp_expr)),
			       BITS_PER_WORD)
		  && known_lt (GET_MODE_PRECISION (GET_MODE (temp_expr)),
			       HOST_BITS_PER_INT)
		  && (reg_stat[REGNO (temp_expr)].nonzero_bits
		      != GET_MODE_MASK (word_mode))))
	   && ! (GET_CODE (SET_DEST (XVECEXP (newpat, 0, 1))) == SUBREG
		 && (temp_expr = SUBREG_REG (SET_DEST (XVECEXP (newpat, 0, 1))),
		     (REG_P (temp_expr)
		      && reg_stat[REGNO (temp_expr)].nonzero_bits != 0
		      && known_lt (GET_MODE_PRECISION (GET_MODE (temp_expr)),
				   BITS_PER_WORD)
		      && known_lt (GET_MODE_PRECISION (GET_MODE (temp_expr)),
				   HOST_BITS_PER_INT)
		      && (reg_stat[REGNO (temp_expr)].nonzero_bits
			  != GET_MODE_MASK (word_mode)))))
	   && ! reg_overlap_mentioned_p (SET_DEST (XVECEXP (newpat, 0, 1)),
					 SET_SRC (XVECEXP (newpat, 0, 1)))
	   && ! find_reg_note (i3, REG_UNUSED,
			       SET_DEST (XVECEXP (newpat, 0, 0))))
    {
      rtx ni2dest;

      newi2pat = XVECEXP (newpat, 0, 0);
      ni2dest = SET_DEST (XVECEXP (newpat, 0, 0));
      newpat = XVECEXP (newpat, 0, 1);
      SUBST (SET_SRC (newpat),
	     gen_lowpart (GET_MODE (SET_SRC (newpat)), ni2dest));
      i2_code_number = recog_for_combine (&newi2pat, i2, &new_i2_notes);

      if (i2_code_number >= 0)
	insn_code_number = recog_for_combine (&newpat, i3, &new_i3_notes);

      if (insn_code_number >= 0)
	swap_i2i3 = 1;
    }

  /* Similarly, check for a case where we have a PARALLEL of two independent
     SETs but we started with three insns.  In this case, we can do the sets
     as two separate insns.  This case occurs when some SET allows two
     other insns to combine, but the destination of that SET is still live.

     Also do this if we started with two insns and (at least) one of the
     resulting sets is a noop; this noop will be deleted later.

     Also do this if we started with two insns neither of which was a simple
     move.  */

  else if (insn_code_number < 0 && asm_noperands (newpat) < 0
	   && GET_CODE (newpat) == PARALLEL
	   && XVECLEN (newpat, 0) == 2
	   && GET_CODE (XVECEXP (newpat, 0, 0)) == SET
	   && GET_CODE (XVECEXP (newpat, 0, 1)) == SET
	   && (i1
	       || set_noop_p (XVECEXP (newpat, 0, 0))
	       || set_noop_p (XVECEXP (newpat, 0, 1))
	       || (!i2_was_move && !i3_was_move))
	   && GET_CODE (SET_DEST (XVECEXP (newpat, 0, 0))) != ZERO_EXTRACT
	   && GET_CODE (SET_DEST (XVECEXP (newpat, 0, 0))) != STRICT_LOW_PART
	   && GET_CODE (SET_DEST (XVECEXP (newpat, 0, 1))) != ZERO_EXTRACT
	   && GET_CODE (SET_DEST (XVECEXP (newpat, 0, 1))) != STRICT_LOW_PART
	   && ! reg_referenced_p (SET_DEST (XVECEXP (newpat, 0, 1)),
				  XVECEXP (newpat, 0, 0))
	   && ! reg_referenced_p (SET_DEST (XVECEXP (newpat, 0, 0)),
				  XVECEXP (newpat, 0, 1))
	   && ! (contains_muldiv (SET_SRC (XVECEXP (newpat, 0, 0)))
		 && contains_muldiv (SET_SRC (XVECEXP (newpat, 0, 1)))))
    {
      rtx set0 = XVECEXP (newpat, 0, 0);
      rtx set1 = XVECEXP (newpat, 0, 1);

      /* Normally, it doesn't matter which of the two is done first,
	 but the one that references cc0 can't be the second, and
	 one which uses any regs/memory set in between i2 and i3 can't
	 be first.  The PARALLEL might also have been pre-existing in i3,
	 so we need to make sure that we won't wrongly hoist a SET to i2
	 that would conflict with a death note present in there, or would
	 have its dest modified between i2 and i3.  */
      if (!modified_between_p (SET_SRC (set1), i2, i3)
	  && !(REG_P (SET_DEST (set1))
	       && find_reg_note (i2, REG_DEAD, SET_DEST (set1)))
	  && !(GET_CODE (SET_DEST (set1)) == SUBREG
	       && find_reg_note (i2, REG_DEAD,
				 SUBREG_REG (SET_DEST (set1))))
	  && !modified_between_p (SET_DEST (set1), i2, i3)
	  && (!HAVE_cc0 || !reg_referenced_p (cc0_rtx, set0))
	  /* If I3 is a jump, ensure that set0 is a jump so that
	     we do not create invalid RTL.  */
	  && (!JUMP_P (i3) || SET_DEST (set0) == pc_rtx)
	 )
	{
	  newi2pat = set1;
	  newpat = set0;
	}
      else if (!modified_between_p (SET_SRC (set0), i2, i3)
	       && !(REG_P (SET_DEST (set0))
		    && find_reg_note (i2, REG_DEAD, SET_DEST (set0)))
	       && !(GET_CODE (SET_DEST (set0)) == SUBREG
		    && find_reg_note (i2, REG_DEAD,
				      SUBREG_REG (SET_DEST (set0))))
	       && !modified_between_p (SET_DEST (set0), i2, i3)
	       && (!HAVE_cc0 || !reg_referenced_p (cc0_rtx, set1))
	       /* If I3 is a jump, ensure that set1 is a jump so that
		  we do not create invalid RTL.  */
	       && (!JUMP_P (i3) || SET_DEST (set1) == pc_rtx)
	      )
	{
	  newi2pat = set0;
	  newpat = set1;
	}
      else
	{
	  undo_all ();
	  return 0;
	}

      i2_code_number = recog_for_combine (&newi2pat, i2, &new_i2_notes);

      if (i2_code_number >= 0)
	{
	  /* recog_for_combine might have added CLOBBERs to newi2pat.
	     Make sure NEWPAT does not depend on the clobbered regs.  */
	  if (GET_CODE (newi2pat) == PARALLEL)
	    {
	      for (i = XVECLEN (newi2pat, 0) - 1; i >= 0; i--)
		if (GET_CODE (XVECEXP (newi2pat, 0, i)) == CLOBBER)
		  {
		    rtx reg = XEXP (XVECEXP (newi2pat, 0, i), 0);
		    if (reg_overlap_mentioned_p (reg, newpat))
		      {
			undo_all ();
			return 0;
		      }
		  }
	    }

	  insn_code_number = recog_for_combine (&newpat, i3, &new_i3_notes);

	  if (insn_code_number >= 0)
	    split_i2i3 = 1;
	}
    }

  /* If it still isn't recognized, fail and change things back the way they
     were.  */
  if ((insn_code_number < 0
       /* Is the result a reasonable ASM_OPERANDS?  */
       && (! check_asm_operands (newpat) || added_sets_1 || added_sets_2)))
    {
      undo_all ();
      return 0;
    }

  /* If we had to change another insn, make sure it is valid also.  */
  if (undobuf.other_insn)
    {
      CLEAR_HARD_REG_SET (newpat_used_regs);

      other_pat = PATTERN (undobuf.other_insn);
      other_code_number = recog_for_combine (&other_pat, undobuf.other_insn,
					     &new_other_notes);

      if (other_code_number < 0 && ! check_asm_operands (other_pat))
	{
	  undo_all ();
	  return 0;
	}
    }

  /* If I2 is the CC0 setter and I3 is the CC0 user then check whether
     they are adjacent to each other or not.  */
  if (HAVE_cc0)
    {
      rtx_insn *p = prev_nonnote_insn (i3);
      if (p && p != i2 && NONJUMP_INSN_P (p) && newi2pat
	  && sets_cc0_p (newi2pat))
	{
	  undo_all ();
	  return 0;
	}
    }

  /* Only allow this combination if insn_cost reports that the
     replacement instructions are cheaper than the originals.  */
  if (!combine_validate_cost (i0, i1, i2, i3, newpat, newi2pat, other_pat))
    {
      undo_all ();
      return 0;
    }

  if (MAY_HAVE_DEBUG_BIND_INSNS)
    {
      struct undo *undo;

      for (undo = undobuf.undos; undo; undo = undo->next)
	if (undo->kind == UNDO_MODE)
	  {
	    rtx reg = *undo->where.r;
	    machine_mode new_mode = GET_MODE (reg);
	    machine_mode old_mode = undo->old_contents.m;

	    /* Temporarily revert mode back.  */
	    adjust_reg_mode (reg, old_mode);

	    if (reg == i2dest && i2scratch)
	      {
		/* If we used i2dest as a scratch register with a
		   different mode, substitute it for the original
		   i2src while its original mode is temporarily
		   restored, and then clear i2scratch so that we don't
		   do it again later.  */
		propagate_for_debug (i2, last_combined_insn, reg, i2src,
				     this_basic_block);
		i2scratch = false;
		/* Put back the new mode.  */
		adjust_reg_mode (reg, new_mode);
	      }
	    else
	      {
		rtx tempreg = gen_raw_REG (old_mode, REGNO (reg));
		rtx_insn *first, *last;

		if (reg == i2dest)
		  {
		    first = i2;
		    last = last_combined_insn;
		  }
		else
		  {
		    first = i3;
		    last = undobuf.other_insn;
		    gcc_assert (last);
		    if (DF_INSN_LUID (last)
			< DF_INSN_LUID (last_combined_insn))
		      last = last_combined_insn;
		  }

		/* We're dealing with a reg that changed mode but not
		   meaning, so we want to turn it into a subreg for
		   the new mode.  However, because of REG sharing and
		   because its mode had already changed, we have to do
		   it in two steps.  First, replace any debug uses of
		   reg, with its original mode temporarily restored,
		   with this copy we have created; then, replace the
		   copy with the SUBREG of the original shared reg,
		   once again changed to the new mode.  */
		propagate_for_debug (first, last, reg, tempreg,
				     this_basic_block);
		adjust_reg_mode (reg, new_mode);
		propagate_for_debug (first, last, tempreg,
				     lowpart_subreg (old_mode, reg, new_mode),
				     this_basic_block);
	      }
	  }
    }

  /* If we will be able to accept this, we have made a
     change to the destination of I3.  This requires us to
     do a few adjustments.  */

  if (changed_i3_dest)
    {
      PATTERN (i3) = newpat;
      adjust_for_new_dest (i3);
    }

  /* We now know that we can do this combination.  Merge the insns and
     update the status of registers and LOG_LINKS.  */

  if (undobuf.other_insn)
    {
      rtx note, next;

      PATTERN (undobuf.other_insn) = other_pat;

      /* If any of the notes in OTHER_INSN were REG_DEAD or REG_UNUSED,
	 ensure that they are still valid.  Then add any non-duplicate
	 notes added by recog_for_combine.  */
      for (note = REG_NOTES (undobuf.other_insn); note; note = next)
	{
	  next = XEXP (note, 1);

	  if ((REG_NOTE_KIND (note) == REG_DEAD
	       && !reg_referenced_p (XEXP (note, 0),
				     PATTERN (undobuf.other_insn)))
	      ||(REG_NOTE_KIND (note) == REG_UNUSED
		 && !reg_set_p (XEXP (note, 0),
				PATTERN (undobuf.other_insn)))
	      /* Simply drop equal note since it may be no longer valid
		 for other_insn.  It may be possible to record that CC
		 register is changed and only discard those notes, but
		 in practice it's unnecessary complication and doesn't
		 give any meaningful improvement.

		 See PR78559.  */
	      || REG_NOTE_KIND (note) == REG_EQUAL
	      || REG_NOTE_KIND (note) == REG_EQUIV)
	    remove_note (undobuf.other_insn, note);
	}

      distribute_notes  (new_other_notes, undobuf.other_insn,
			undobuf.other_insn, NULL, NULL_RTX, NULL_RTX,
			NULL_RTX);
    }

  if (swap_i2i3)
    {
      /* I3 now uses what used to be its destination and which is now
	 I2's destination.  This requires us to do a few adjustments.  */
      PATTERN (i3) = newpat;
      adjust_for_new_dest (i3);
    }

  if (swap_i2i3 || split_i2i3)
    {
      /* We might need a LOG_LINK from I3 to I2.  But then we used to
	 have one, so we still will.

	 However, some later insn might be using I2's dest and have
	 a LOG_LINK pointing at I3.  We should change it to point at
	 I2 instead.  */

      /* newi2pat is usually a SET here; however, recog_for_combine might
	 have added some clobbers.  */
      rtx x = newi2pat;
      if (GET_CODE (x) == PARALLEL)
	x = XVECEXP (newi2pat, 0, 0);

      /* It can only be a SET of a REG or of a SUBREG of a REG.  */
      unsigned int regno = reg_or_subregno (SET_DEST (x));

      bool done = false;
      for (rtx_insn *insn = NEXT_INSN (i3);
	   !done
	   && insn
	   && NONDEBUG_INSN_P (insn)
	   && BLOCK_FOR_INSN (insn) == this_basic_block;
	   insn = NEXT_INSN (insn))
	{
	  struct insn_link *link;
	  FOR_EACH_LOG_LINK (link, insn)
	    if (link->insn == i3 && link->regno == regno)
	      {
		link->insn = i2;
		done = true;
		break;
	      }
	}
    }

  {
    rtx i3notes, i2notes, i1notes = 0, i0notes = 0;
    struct insn_link *i3links, *i2links, *i1links = 0, *i0links = 0;
    rtx midnotes = 0;
    int from_luid;
    /* Compute which registers we expect to eliminate.  newi2pat may be setting
       either i3dest or i2dest, so we must check it.  */
    rtx elim_i2 = ((newi2pat && reg_set_p (i2dest, newi2pat))
		   || i2dest_in_i2src || i2dest_in_i1src || i2dest_in_i0src
		   || !i2dest_killed
		   ? 0 : i2dest);
    /* For i1, we need to compute both local elimination and global
       elimination information with respect to newi2pat because i1dest
       may be the same as i3dest, in which case newi2pat may be setting
       i1dest.  Global information is used when distributing REG_DEAD
       note for i2 and i3, in which case it does matter if newi2pat sets
       i1dest or not.

       Local information is used when distributing REG_DEAD note for i1,
       in which case it doesn't matter if newi2pat sets i1dest or not.
       See PR62151, if we have four insns combination:
	   i0: r0 <- i0src
	   i1: r1 <- i1src (using r0)
		     REG_DEAD (r0)
	   i2: r0 <- i2src (using r1)
	   i3: r3 <- i3src (using r0)
	   ix: using r0
       From i1's point of view, r0 is eliminated, no matter if it is set
       by newi2pat or not.  In other words, REG_DEAD info for r0 in i1
       should be discarded.

       Note local information only affects cases in forms like "I1->I2->I3",
       "I0->I1->I2->I3" or "I0&I1->I2, I2->I3".  For other cases like
       "I0->I1, I1&I2->I3" or "I1&I2->I3", newi2pat won't set i1dest or
       i0dest anyway.  */
    rtx local_elim_i1 = (i1 == 0 || i1dest_in_i1src || i1dest_in_i0src
			 || !i1dest_killed
			 ? 0 : i1dest);
    rtx elim_i1 = (local_elim_i1 == 0
		   || (newi2pat && reg_set_p (i1dest, newi2pat))
		   ? 0 : i1dest);
    /* Same case as i1.  */
    rtx local_elim_i0 = (i0 == 0 || i0dest_in_i0src || !i0dest_killed
			 ? 0 : i0dest);
    rtx elim_i0 = (local_elim_i0 == 0
		   || (newi2pat && reg_set_p (i0dest, newi2pat))
		   ? 0 : i0dest);

    /* Get the old REG_NOTES and LOG_LINKS from all our insns and
       clear them.  */
    i3notes = REG_NOTES (i3), i3links = LOG_LINKS (i3);
    i2notes = REG_NOTES (i2), i2links = LOG_LINKS (i2);
    if (i1)
      i1notes = REG_NOTES (i1), i1links = LOG_LINKS (i1);
    if (i0)
      i0notes = REG_NOTES (i0), i0links = LOG_LINKS (i0);

    /* Ensure that we do not have something that should not be shared but
       occurs multiple times in the new insns.  Check this by first
       resetting all the `used' flags and then copying anything is shared.  */

    reset_used_flags (i3notes);
    reset_used_flags (i2notes);
    reset_used_flags (i1notes);
    reset_used_flags (i0notes);
    reset_used_flags (newpat);
    reset_used_flags (newi2pat);
    if (undobuf.other_insn)
      reset_used_flags (PATTERN (undobuf.other_insn));

    i3notes = copy_rtx_if_shared (i3notes);
    i2notes = copy_rtx_if_shared (i2notes);
    i1notes = copy_rtx_if_shared (i1notes);
    i0notes = copy_rtx_if_shared (i0notes);
    newpat = copy_rtx_if_shared (newpat);
    newi2pat = copy_rtx_if_shared (newi2pat);
    if (undobuf.other_insn)
      reset_used_flags (PATTERN (undobuf.other_insn));

    INSN_CODE (i3) = insn_code_number;
    PATTERN (i3) = newpat;

    if (CALL_P (i3) && CALL_INSN_FUNCTION_USAGE (i3))
      {
	for (rtx link = CALL_INSN_FUNCTION_USAGE (i3); link;
	     link = XEXP (link, 1))
	  {
	    if (substed_i2)
	      {
		/* I2SRC must still be meaningful at this point.  Some
		   splitting operations can invalidate I2SRC, but those
		   operations do not apply to calls.  */
		gcc_assert (i2src);
		XEXP (link, 0) = simplify_replace_rtx (XEXP (link, 0),
						       i2dest, i2src);
	      }
	    if (substed_i1)
	      XEXP (link, 0) = simplify_replace_rtx (XEXP (link, 0),
						     i1dest, i1src);
	    if (substed_i0)
	      XEXP (link, 0) = simplify_replace_rtx (XEXP (link, 0),
						     i0dest, i0src);
	  }
      }

    if (undobuf.other_insn)
      INSN_CODE (undobuf.other_insn) = other_code_number;

    /* We had one special case above where I2 had more than one set and
       we replaced a destination of one of those sets with the destination
       of I3.  In that case, we have to update LOG_LINKS of insns later
       in this basic block.  Note that this (expensive) case is rare.

       Also, in this case, we must pretend that all REG_NOTEs for I2
       actually came from I3, so that REG_UNUSED notes from I2 will be
       properly handled.  */

    if (i3_subst_into_i2)
      {
	for (i = 0; i < XVECLEN (PATTERN (i2), 0); i++)
	  if ((GET_CODE (XVECEXP (PATTERN (i2), 0, i)) == SET
	       || GET_CODE (XVECEXP (PATTERN (i2), 0, i)) == CLOBBER)
	      && REG_P (SET_DEST (XVECEXP (PATTERN (i2), 0, i)))
	      && SET_DEST (XVECEXP (PATTERN (i2), 0, i)) != i2dest
	      && ! find_reg_note (i2, REG_UNUSED,
				  SET_DEST (XVECEXP (PATTERN (i2), 0, i))))
	    for (temp_insn = NEXT_INSN (i2);
		 temp_insn
		 && (this_basic_block->next_bb == EXIT_BLOCK_PTR_FOR_FN (cfun)
		     || BB_HEAD (this_basic_block) != temp_insn);
		 temp_insn = NEXT_INSN (temp_insn))
	      if (temp_insn != i3 && NONDEBUG_INSN_P (temp_insn))
		FOR_EACH_LOG_LINK (link, temp_insn)
		  if (link->insn == i2)
		    link->insn = i3;

	if (i3notes)
	  {
	    rtx link = i3notes;
	    while (XEXP (link, 1))
	      link = XEXP (link, 1);
	    XEXP (link, 1) = i2notes;
	  }
	else
	  i3notes = i2notes;
	i2notes = 0;
      }

    LOG_LINKS (i3) = NULL;
    REG_NOTES (i3) = 0;
    LOG_LINKS (i2) = NULL;
    REG_NOTES (i2) = 0;

    if (newi2pat)
      {
	if (MAY_HAVE_DEBUG_BIND_INSNS && i2scratch)
	  propagate_for_debug (i2, last_combined_insn, i2dest, i2src,
			       this_basic_block);
	INSN_CODE (i2) = i2_code_number;
	PATTERN (i2) = newi2pat;
      }
    else
      {
	if (MAY_HAVE_DEBUG_BIND_INSNS && i2src)
	  propagate_for_debug (i2, last_combined_insn, i2dest, i2src,
			       this_basic_block);
	SET_INSN_DELETED (i2);
      }

    if (i1)
      {
	LOG_LINKS (i1) = NULL;
	REG_NOTES (i1) = 0;
	if (MAY_HAVE_DEBUG_BIND_INSNS)
	  propagate_for_debug (i1, last_combined_insn, i1dest, i1src,
			       this_basic_block);
	SET_INSN_DELETED (i1);
      }

    if (i0)
      {
	LOG_LINKS (i0) = NULL;
	REG_NOTES (i0) = 0;
	if (MAY_HAVE_DEBUG_BIND_INSNS)
	  propagate_for_debug (i0, last_combined_insn, i0dest, i0src,
			       this_basic_block);
	SET_INSN_DELETED (i0);
      }

    /* Get death notes for everything that is now used in either I3 or
       I2 and used to die in a previous insn.  If we built two new
       patterns, move from I1 to I2 then I2 to I3 so that we get the
       proper movement on registers that I2 modifies.  */

    if (i0)
      from_luid = DF_INSN_LUID (i0);
    else if (i1)
      from_luid = DF_INSN_LUID (i1);
    else
      from_luid = DF_INSN_LUID (i2);
    if (newi2pat)
      move_deaths (newi2pat, NULL_RTX, from_luid, i2, &midnotes);
    move_deaths (newpat, newi2pat, from_luid, i3, &midnotes);

    /* Distribute all the LOG_LINKS and REG_NOTES from I1, I2, and I3.  */
    if (i3notes)
      distribute_notes (i3notes, i3, i3, newi2pat ? i2 : NULL,
			elim_i2, elim_i1, elim_i0);
    if (i2notes)
      distribute_notes (i2notes, i2, i3, newi2pat ? i2 : NULL,
			elim_i2, elim_i1, elim_i0);
    if (i1notes)
      distribute_notes (i1notes, i1, i3, newi2pat ? i2 : NULL,
			elim_i2, local_elim_i1, local_elim_i0);
    if (i0notes)
      distribute_notes (i0notes, i0, i3, newi2pat ? i2 : NULL,
			elim_i2, elim_i1, local_elim_i0);
    if (midnotes)
      distribute_notes (midnotes, NULL, i3, newi2pat ? i2 : NULL,
			elim_i2, elim_i1, elim_i0);

    /* Distribute any notes added to I2 or I3 by recog_for_combine.  We
       know these are REG_UNUSED and want them to go to the desired insn,
       so we always pass it as i3.  */

    if (newi2pat && new_i2_notes)
      distribute_notes (new_i2_notes, i2, i2, NULL, NULL_RTX, NULL_RTX,
			NULL_RTX);

    if (new_i3_notes)
      distribute_notes (new_i3_notes, i3, i3, NULL, NULL_RTX, NULL_RTX,
			NULL_RTX);

    /* If I3DEST was used in I3SRC, it really died in I3.  We may need to
       put a REG_DEAD note for it somewhere.  If NEWI2PAT exists and sets
       I3DEST, the death must be somewhere before I2, not I3.  If we passed I3
       in that case, it might delete I2.  Similarly for I2 and I1.
       Show an additional death due to the REG_DEAD note we make here.  If
       we discard it in distribute_notes, we will decrement it again.  */

    if (i3dest_killed)
      {
	rtx new_note = alloc_reg_note (REG_DEAD, i3dest_killed, NULL_RTX);
	if (newi2pat && reg_set_p (i3dest_killed, newi2pat))
	  distribute_notes (new_note, NULL, i2, NULL, elim_i2,
			    elim_i1, elim_i0);
	else
	  distribute_notes (new_note, NULL, i3, newi2pat ? i2 : NULL,
			    elim_i2, elim_i1, elim_i0);
      }

    if (i2dest_in_i2src)
      {
	rtx new_note = alloc_reg_note (REG_DEAD, i2dest, NULL_RTX);
	if (newi2pat && reg_set_p (i2dest, newi2pat))
	  distribute_notes (new_note,  NULL, i2, NULL, NULL_RTX,
			    NULL_RTX, NULL_RTX);
	else
	  distribute_notes (new_note, NULL, i3, newi2pat ? i2 : NULL,
			    NULL_RTX, NULL_RTX, NULL_RTX);
      }

    if (i1dest_in_i1src)
      {
	rtx new_note = alloc_reg_note (REG_DEAD, i1dest, NULL_RTX);
	if (newi2pat && reg_set_p (i1dest, newi2pat))
	  distribute_notes (new_note, NULL, i2, NULL, NULL_RTX,
			    NULL_RTX, NULL_RTX);
	else
	  distribute_notes (new_note, NULL, i3, newi2pat ? i2 : NULL,
			    NULL_RTX, NULL_RTX, NULL_RTX);
      }

    if (i0dest_in_i0src)
      {
	rtx new_note = alloc_reg_note (REG_DEAD, i0dest, NULL_RTX);
	if (newi2pat && reg_set_p (i0dest, newi2pat))
	  distribute_notes (new_note, NULL, i2, NULL, NULL_RTX,
			    NULL_RTX, NULL_RTX);
	else
	  distribute_notes (new_note, NULL, i3, newi2pat ? i2 : NULL,
			    NULL_RTX, NULL_RTX, NULL_RTX);
      }

    distribute_links (i3links);
    distribute_links (i2links);
    distribute_links (i1links);
    distribute_links (i0links);

    if (REG_P (i2dest))
      {
	struct insn_link *link;
	rtx_insn *i2_insn = 0;
	rtx i2_val = 0, set;

	/* The insn that used to set this register doesn't exist, and
	   this life of the register may not exist either.  See if one of
	   I3's links points to an insn that sets I2DEST.  If it does,
	   that is now the last known value for I2DEST. If we don't update
	   this and I2 set the register to a value that depended on its old
	   contents, we will get confused.  If this insn is used, thing
	   will be set correctly in combine_instructions.  */
	FOR_EACH_LOG_LINK (link, i3)
	  if ((set = single_set (link->insn)) != 0
	      && rtx_equal_p (i2dest, SET_DEST (set)))
	    i2_insn = link->insn, i2_val = SET_SRC (set);

	record_value_for_reg (i2dest, i2_insn, i2_val);

	/* If the reg formerly set in I2 died only once and that was in I3,
	   zero its use count so it won't make `reload' do any work.  */
	if (! added_sets_2
	    && (newi2pat == 0 || ! reg_mentioned_p (i2dest, newi2pat))
	    && ! i2dest_in_i2src
	    && REGNO (i2dest) < reg_n_sets_max)
	  INC_REG_N_SETS (REGNO (i2dest), -1);
      }

    if (i1 && REG_P (i1dest))
      {
	struct insn_link *link;
	rtx_insn *i1_insn = 0;
	rtx i1_val = 0, set;

	FOR_EACH_LOG_LINK (link, i3)
	  if ((set = single_set (link->insn)) != 0
	      && rtx_equal_p (i1dest, SET_DEST (set)))
	    i1_insn = link->insn, i1_val = SET_SRC (set);

	record_value_for_reg (i1dest, i1_insn, i1_val);

	if (! added_sets_1
	    && ! i1dest_in_i1src
	    && REGNO (i1dest) < reg_n_sets_max)
	  INC_REG_N_SETS (REGNO (i1dest), -1);
      }

    if (i0 && REG_P (i0dest))
      {
	struct insn_link *link;
	rtx_insn *i0_insn = 0;
	rtx i0_val = 0, set;

	FOR_EACH_LOG_LINK (link, i3)
	  if ((set = single_set (link->insn)) != 0
	      && rtx_equal_p (i0dest, SET_DEST (set)))
	    i0_insn = link->insn, i0_val = SET_SRC (set);

	record_value_for_reg (i0dest, i0_insn, i0_val);

	if (! added_sets_0
	    && ! i0dest_in_i0src
	    && REGNO (i0dest) < reg_n_sets_max)
	  INC_REG_N_SETS (REGNO (i0dest), -1);
      }

    /* Update reg_stat[].nonzero_bits et al for any changes that may have
       been made to this insn.  The order is important, because newi2pat
       can affect nonzero_bits of newpat.  */
    if (newi2pat)
      note_stores (newi2pat, set_nonzero_bits_and_sign_copies, NULL);
    note_stores (newpat, set_nonzero_bits_and_sign_copies, NULL);
  }

  if (undobuf.other_insn != NULL_RTX)
    {
      if (dump_file)
	{
	  fprintf (dump_file, "modifying other_insn ");
	  dump_insn_slim (dump_file, undobuf.other_insn);
	}
      df_insn_rescan (undobuf.other_insn);
    }

  if (i0 && !(NOTE_P (i0) && (NOTE_KIND (i0) == NOTE_INSN_DELETED)))
    {
      if (dump_file)
	{
	  fprintf (dump_file, "modifying insn i0 ");
	  dump_insn_slim (dump_file, i0);
	}
      df_insn_rescan (i0);
    }

  if (i1 && !(NOTE_P (i1) && (NOTE_KIND (i1) == NOTE_INSN_DELETED)))
    {
      if (dump_file)
	{
	  fprintf (dump_file, "modifying insn i1 ");
	  dump_insn_slim (dump_file, i1);
	}
      df_insn_rescan (i1);
    }

  if (i2 && !(NOTE_P (i2) && (NOTE_KIND (i2) == NOTE_INSN_DELETED)))
    {
      if (dump_file)
	{
	  fprintf (dump_file, "modifying insn i2 ");
	  dump_insn_slim (dump_file, i2);
	}
      df_insn_rescan (i2);
    }

  if (i3 && !(NOTE_P (i3) && (NOTE_KIND (i3) == NOTE_INSN_DELETED)))
    {
      if (dump_file)
	{
	  fprintf (dump_file, "modifying insn i3 ");
	  dump_insn_slim (dump_file, i3);
	}
      df_insn_rescan (i3);
    }

  /* Set new_direct_jump_p if a new return or simple jump instruction
     has been created.  Adjust the CFG accordingly.  */
  if (returnjump_p (i3) || any_uncondjump_p (i3))
    {
      *new_direct_jump_p = 1;
      mark_jump_label (PATTERN (i3), i3, 0);
      update_cfg_for_uncondjump (i3);
    }

  if (undobuf.other_insn != NULL_RTX
      && (returnjump_p (undobuf.other_insn)
	  || any_uncondjump_p (undobuf.other_insn)))
    {
      *new_direct_jump_p = 1;
      update_cfg_for_uncondjump (undobuf.other_insn);
    }

  if (GET_CODE (PATTERN (i3)) == TRAP_IF
      && XEXP (PATTERN (i3), 0) == const1_rtx)
    {
      basic_block bb = BLOCK_FOR_INSN (i3);
      gcc_assert (bb);
      remove_edge (split_block (bb, i3));
      emit_barrier_after_bb (bb);
      *new_direct_jump_p = 1;
    }

  if (undobuf.other_insn
      && GET_CODE (PATTERN (undobuf.other_insn)) == TRAP_IF
      && XEXP (PATTERN (undobuf.other_insn), 0) == const1_rtx)
    {
      basic_block bb = BLOCK_FOR_INSN (undobuf.other_insn);
      gcc_assert (bb);
      remove_edge (split_block (bb, undobuf.other_insn));
      emit_barrier_after_bb (bb);
      *new_direct_jump_p = 1;
    }

  /* A noop might also need cleaning up of CFG, if it comes from the
     simplification of a jump.  */
  if (JUMP_P (i3)
      && GET_CODE (newpat) == SET
      && SET_SRC (newpat) == pc_rtx
      && SET_DEST (newpat) == pc_rtx)
    {
      *new_direct_jump_p = 1;
      update_cfg_for_uncondjump (i3);
    }

  if (undobuf.other_insn != NULL_RTX
      && JUMP_P (undobuf.other_insn)
      && GET_CODE (PATTERN (undobuf.other_insn)) == SET
      && SET_SRC (PATTERN (undobuf.other_insn)) == pc_rtx
      && SET_DEST (PATTERN (undobuf.other_insn)) == pc_rtx)
    {
      *new_direct_jump_p = 1;
      update_cfg_for_uncondjump (undobuf.other_insn);
    }

  combine_successes++;
  undo_commit ();

  rtx_insn *ret = newi2pat ? i2 : i3;
  if (added_links_insn && DF_INSN_LUID (added_links_insn) < DF_INSN_LUID (ret))
    ret = added_links_insn;
  if (added_notes_insn && DF_INSN_LUID (added_notes_insn) < DF_INSN_LUID (ret))
    ret = added_notes_insn;

  return ret;
}

/* Get a marker for undoing to the current state.  */

static void *
get_undo_marker (void)
{
  return undobuf.undos;
}

/* Undo the modifications up to the marker.  */

static void
undo_to_marker (void *marker)
{
  struct undo *undo, *next;

  for (undo = undobuf.undos; undo != marker; undo = next)
    {
      gcc_assert (undo);

      next = undo->next;
      switch (undo->kind)
	{
	case UNDO_RTX:
	  *undo->where.r = undo->old_contents.r;
	  break;
	case UNDO_INT:
	  *undo->where.i = undo->old_contents.i;
	  break;
	case UNDO_MODE:
	  adjust_reg_mode (*undo->where.r, undo->old_contents.m);
	  break;
	case UNDO_LINKS:
	  *undo->where.l = undo->old_contents.l;
	  break;
	default:
	  gcc_unreachable ();
	}

      undo->next = undobuf.frees;
      undobuf.frees = undo;
    }

  undobuf.undos = (struct undo *) marker;
}

/* Undo all the modifications recorded in undobuf.  */

static void
undo_all (void)
{
  undo_to_marker (0);
}

/* We've committed to accepting the changes we made.  Move all
   of the undos to the free list.  */

static void
undo_commit (void)
{
  struct undo *undo, *next;

  for (undo = undobuf.undos; undo; undo = next)
    {
      next = undo->next;
      undo->next = undobuf.frees;
      undobuf.frees = undo;
    }
  undobuf.undos = 0;
}

/* Find the innermost point within the rtx at LOC, possibly LOC itself,
   where we have an arithmetic expression and return that point.  LOC will
   be inside INSN.

   try_combine will call this function to see if an insn can be split into
   two insns.  */

static rtx *
find_split_point (rtx *loc, rtx_insn *insn, bool set_src)
{
  rtx x = *loc;
  enum rtx_code code = GET_CODE (x);
  rtx *split;
  unsigned HOST_WIDE_INT len = 0;
  HOST_WIDE_INT pos = 0;
  int unsignedp = 0;
  rtx inner = NULL_RTX;
  scalar_int_mode mode, inner_mode;

  /* First special-case some codes.  */
  switch (code)
    {
    case SUBREG:
#ifdef INSN_SCHEDULING
      /* If we are making a paradoxical SUBREG invalid, it becomes a split
	 point.  */
      if (MEM_P (SUBREG_REG (x)))
	return loc;
#endif
      return find_split_point (&SUBREG_REG (x), insn, false);

    case MEM:
      /* If we have (mem (const ..)) or (mem (symbol_ref ...)), split it
	 using LO_SUM and HIGH.  */
      if (HAVE_lo_sum && (GET_CODE (XEXP (x, 0)) == CONST
			  || GET_CODE (XEXP (x, 0)) == SYMBOL_REF))
	{
	  machine_mode address_mode = get_address_mode (x);

	  SUBST (XEXP (x, 0),
		 gen_rtx_LO_SUM (address_mode,
				 gen_rtx_HIGH (address_mode, XEXP (x, 0)),
				 XEXP (x, 0)));
	  return &XEXP (XEXP (x, 0), 0);
	}

      /* If we have a PLUS whose second operand is a constant and the
	 address is not valid, perhaps will can split it up using
	 the machine-specific way to split large constants.  We use
	 the first pseudo-reg (one of the virtual regs) as a placeholder;
	 it will not remain in the result.  */
      if (GET_CODE (XEXP (x, 0)) == PLUS
	  && CONST_INT_P (XEXP (XEXP (x, 0), 1))
	  && ! memory_address_addr_space_p (GET_MODE (x), XEXP (x, 0),
					    MEM_ADDR_SPACE (x)))
	{
	  rtx reg = regno_reg_rtx[FIRST_PSEUDO_REGISTER];
	  rtx_insn *seq = combine_split_insns (gen_rtx_SET (reg, XEXP (x, 0)),
					       subst_insn);

	  /* This should have produced two insns, each of which sets our
	     placeholder.  If the source of the second is a valid address,
	     we can make put both sources together and make a split point
	     in the middle.  */

	  if (seq
	      && NEXT_INSN (seq) != NULL_RTX
	      && NEXT_INSN (NEXT_INSN (seq)) == NULL_RTX
	      && NONJUMP_INSN_P (seq)
	      && GET_CODE (PATTERN (seq)) == SET
	      && SET_DEST (PATTERN (seq)) == reg
	      && ! reg_mentioned_p (reg,
				    SET_SRC (PATTERN (seq)))
	      && NONJUMP_INSN_P (NEXT_INSN (seq))
	      && GET_CODE (PATTERN (NEXT_INSN (seq))) == SET
	      && SET_DEST (PATTERN (NEXT_INSN (seq))) == reg
	      && memory_address_addr_space_p
		   (GET_MODE (x), SET_SRC (PATTERN (NEXT_INSN (seq))),
		    MEM_ADDR_SPACE (x)))
	    {
	      rtx src1 = SET_SRC (PATTERN (seq));
	      rtx src2 = SET_SRC (PATTERN (NEXT_INSN (seq)));

	      /* Replace the placeholder in SRC2 with SRC1.  If we can
		 find where in SRC2 it was placed, that can become our
		 split point and we can replace this address with SRC2.
		 Just try two obvious places.  */

	      src2 = replace_rtx (src2, reg, src1);
	      split = 0;
	      if (XEXP (src2, 0) == src1)
		split = &XEXP (src2, 0);
	      else if (GET_RTX_FORMAT (GET_CODE (XEXP (src2, 0)))[0] == 'e'
		       && XEXP (XEXP (src2, 0), 0) == src1)
		split = &XEXP (XEXP (src2, 0), 0);

	      if (split)
		{
		  SUBST (XEXP (x, 0), src2);
		  return split;
		}
	    }

	  /* If that didn't work, perhaps the first operand is complex and
	     needs to be computed separately, so make a split point there.
	     This will occur on machines that just support REG + CONST
	     and have a constant moved through some previous computation.  */

	  else if (!OBJECT_P (XEXP (XEXP (x, 0), 0))
		   && ! (GET_CODE (XEXP (XEXP (x, 0), 0)) == SUBREG
			 && OBJECT_P (SUBREG_REG (XEXP (XEXP (x, 0), 0)))))
	    return &XEXP (XEXP (x, 0), 0);
	}

      /* If we have a PLUS whose first operand is complex, try computing it
         separately by making a split there.  */
      if (GET_CODE (XEXP (x, 0)) == PLUS
          && ! memory_address_addr_space_p (GET_MODE (x), XEXP (x, 0),
					    MEM_ADDR_SPACE (x))
          && ! OBJECT_P (XEXP (XEXP (x, 0), 0))
          && ! (GET_CODE (XEXP (XEXP (x, 0), 0)) == SUBREG
                && OBJECT_P (SUBREG_REG (XEXP (XEXP (x, 0), 0)))))
        return &XEXP (XEXP (x, 0), 0);
      break;

    case SET:
      /* If SET_DEST is CC0 and SET_SRC is not an operand, a COMPARE, or a
	 ZERO_EXTRACT, the most likely reason why this doesn't match is that
	 we need to put the operand into a register.  So split at that
	 point.  */

      if (SET_DEST (x) == cc0_rtx
	  && GET_CODE (SET_SRC (x)) != COMPARE
	  && GET_CODE (SET_SRC (x)) != ZERO_EXTRACT
	  && !OBJECT_P (SET_SRC (x))
	  && ! (GET_CODE (SET_SRC (x)) == SUBREG
		&& OBJECT_P (SUBREG_REG (SET_SRC (x)))))
	return &SET_SRC (x);

      /* See if we can split SET_SRC as it stands.  */
      split = find_split_point (&SET_SRC (x), insn, true);
      if (split && split != &SET_SRC (x))
	return split;

      /* See if we can split SET_DEST as it stands.  */
      split = find_split_point (&SET_DEST (x), insn, false);
      if (split && split != &SET_DEST (x))
	return split;

      /* See if this is a bitfield assignment with everything constant.  If
	 so, this is an IOR of an AND, so split it into that.  */
      if (GET_CODE (SET_DEST (x)) == ZERO_EXTRACT
	  && is_a <scalar_int_mode> (GET_MODE (XEXP (SET_DEST (x), 0)),
				     &inner_mode)
	  && HWI_COMPUTABLE_MODE_P (inner_mode)
	  && CONST_INT_P (XEXP (SET_DEST (x), 1))
	  && CONST_INT_P (XEXP (SET_DEST (x), 2))
	  && CONST_INT_P (SET_SRC (x))
	  && ((INTVAL (XEXP (SET_DEST (x), 1))
	       + INTVAL (XEXP (SET_DEST (x), 2)))
	      <= GET_MODE_PRECISION (inner_mode))
	  && ! side_effects_p (XEXP (SET_DEST (x), 0)))
	{
	  HOST_WIDE_INT pos = INTVAL (XEXP (SET_DEST (x), 2));
	  unsigned HOST_WIDE_INT len = INTVAL (XEXP (SET_DEST (x), 1));
	  unsigned HOST_WIDE_INT src = INTVAL (SET_SRC (x));
	  rtx dest = XEXP (SET_DEST (x), 0);
	  unsigned HOST_WIDE_INT mask
	    = (HOST_WIDE_INT_1U << len) - 1;
	  rtx or_mask;

	  if (BITS_BIG_ENDIAN)
	    pos = GET_MODE_PRECISION (inner_mode) - len - pos;

	  or_mask = gen_int_mode (src << pos, inner_mode);
	  if (src == mask)
	    SUBST (SET_SRC (x),
		   simplify_gen_binary (IOR, inner_mode, dest, or_mask));
	  else
	    {
	      rtx negmask = gen_int_mode (~(mask << pos), inner_mode);
	      SUBST (SET_SRC (x),
		     simplify_gen_binary (IOR, inner_mode,
					  simplify_gen_binary (AND, inner_mode,
							       dest, negmask),
					  or_mask));
	    }

	  SUBST (SET_DEST (x), dest);

	  split = find_split_point (&SET_SRC (x), insn, true);
	  if (split && split != &SET_SRC (x))
	    return split;
	}

      /* Otherwise, see if this is an operation that we can split into two.
	 If so, try to split that.  */
      code = GET_CODE (SET_SRC (x));

      switch (code)
	{
	case AND:
	  /* If we are AND'ing with a large constant that is only a single
	     bit and the result is only being used in a context where we
	     need to know if it is zero or nonzero, replace it with a bit
	     extraction.  This will avoid the large constant, which might
	     have taken more than one insn to make.  If the constant were
	     not a valid argument to the AND but took only one insn to make,
	     this is no worse, but if it took more than one insn, it will
	     be better.  */

	  if (CONST_INT_P (XEXP (SET_SRC (x), 1))
	      && REG_P (XEXP (SET_SRC (x), 0))
	      && (pos = exact_log2 (UINTVAL (XEXP (SET_SRC (x), 1)))) >= 7
	      && REG_P (SET_DEST (x))
	      && (split = find_single_use (SET_DEST (x), insn, NULL)) != 0
	      && (GET_CODE (*split) == EQ || GET_CODE (*split) == NE)
	      && XEXP (*split, 0) == SET_DEST (x)
	      && XEXP (*split, 1) == const0_rtx)
	    {
	      rtx extraction = make_extraction (GET_MODE (SET_DEST (x)),
						XEXP (SET_SRC (x), 0),
						pos, NULL_RTX, 1, 1, 0, 0);
	      if (extraction != 0)
		{
		  SUBST (SET_SRC (x), extraction);
		  return find_split_point (loc, insn, false);
		}
	    }
	  break;

	case NE:
	  /* If STORE_FLAG_VALUE is -1, this is (NE X 0) and only one bit of X
	     is known to be on, this can be converted into a NEG of a shift.  */
	  if (STORE_FLAG_VALUE == -1 && XEXP (SET_SRC (x), 1) == const0_rtx
	      && GET_MODE (SET_SRC (x)) == GET_MODE (XEXP (SET_SRC (x), 0))
	      && ((pos = exact_log2 (nonzero_bits (XEXP (SET_SRC (x), 0),
						   GET_MODE (XEXP (SET_SRC (x),
							     0))))) >= 1))
	    {
	      machine_mode mode = GET_MODE (XEXP (SET_SRC (x), 0));
	      rtx pos_rtx = gen_int_shift_amount (mode, pos);
	      SUBST (SET_SRC (x),
		     gen_rtx_NEG (mode,
				  gen_rtx_LSHIFTRT (mode,
						    XEXP (SET_SRC (x), 0),
						    pos_rtx)));

	      split = find_split_point (&SET_SRC (x), insn, true);
	      if (split && split != &SET_SRC (x))
		return split;
	    }
	  break;

	case SIGN_EXTEND:
	  inner = XEXP (SET_SRC (x), 0);

	  /* We can't optimize if either mode is a partial integer
	     mode as we don't know how many bits are significant
	     in those modes.  */
	  if (!is_int_mode (GET_MODE (inner), &inner_mode)
	      || GET_MODE_CLASS (GET_MODE (SET_SRC (x))) == MODE_PARTIAL_INT)
	    break;

	  pos = 0;
	  len = GET_MODE_PRECISION (inner_mode);
	  unsignedp = 0;
	  break;

	case SIGN_EXTRACT:
	case ZERO_EXTRACT:
	  if (is_a <scalar_int_mode> (GET_MODE (XEXP (SET_SRC (x), 0)),
				      &inner_mode)
	      && CONST_INT_P (XEXP (SET_SRC (x), 1))
	      && CONST_INT_P (XEXP (SET_SRC (x), 2)))
	    {
	      inner = XEXP (SET_SRC (x), 0);
	      len = INTVAL (XEXP (SET_SRC (x), 1));
	      pos = INTVAL (XEXP (SET_SRC (x), 2));

	      if (BITS_BIG_ENDIAN)
		pos = GET_MODE_PRECISION (inner_mode) - len - pos;
	      unsignedp = (code == ZERO_EXTRACT);
	    }
	  break;

	default:
	  break;
	}

      if (len
	  && known_subrange_p (pos, len,
			       0, GET_MODE_PRECISION (GET_MODE (inner)))
	  && is_a <scalar_int_mode> (GET_MODE (SET_SRC (x)), &mode))
	{
	  /* For unsigned, we have a choice of a shift followed by an
	     AND or two shifts.  Use two shifts for field sizes where the
	     constant might be too large.  We assume here that we can
	     always at least get 8-bit constants in an AND insn, which is
	     true for every current RISC.  */

	  if (unsignedp && len <= 8)
	    {
	      unsigned HOST_WIDE_INT mask
		= (HOST_WIDE_INT_1U << len) - 1;
	      rtx pos_rtx = gen_int_shift_amount (mode, pos);
	      SUBST (SET_SRC (x),
		     gen_rtx_AND (mode,
				  gen_rtx_LSHIFTRT
				  (mode, gen_lowpart (mode, inner), pos_rtx),
				  gen_int_mode (mask, mode)));

	      split = find_split_point (&SET_SRC (x), insn, true);
	      if (split && split != &SET_SRC (x))
		return split;
	    }
	  else
	    {
	      int left_bits = GET_MODE_PRECISION (mode) - len - pos;
	      int right_bits = GET_MODE_PRECISION (mode) - len;
	      SUBST (SET_SRC (x),
		     gen_rtx_fmt_ee
		     (unsignedp ? LSHIFTRT : ASHIFTRT, mode,
		      gen_rtx_ASHIFT (mode,
				      gen_lowpart (mode, inner),
				      gen_int_shift_amount (mode, left_bits)),
		      gen_int_shift_amount (mode, right_bits)));

	      split = find_split_point (&SET_SRC (x), insn, true);
	      if (split && split != &SET_SRC (x))
		return split;
	    }
	}

      /* See if this is a simple operation with a constant as the second
	 operand.  It might be that this constant is out of range and hence
	 could be used as a split point.  */
      if (BINARY_P (SET_SRC (x))
	  && CONSTANT_P (XEXP (SET_SRC (x), 1))
	  && (OBJECT_P (XEXP (SET_SRC (x), 0))
	      || (GET_CODE (XEXP (SET_SRC (x), 0)) == SUBREG
		  && OBJECT_P (SUBREG_REG (XEXP (SET_SRC (x), 0))))))
	return &XEXP (SET_SRC (x), 1);

      /* Finally, see if this is a simple operation with its first operand
	 not in a register.  The operation might require this operand in a
	 register, so return it as a split point.  We can always do this
	 because if the first operand were another operation, we would have
	 already found it as a split point.  */
      if ((BINARY_P (SET_SRC (x)) || UNARY_P (SET_SRC (x)))
	  && ! register_operand (XEXP (SET_SRC (x), 0), VOIDmode))
	return &XEXP (SET_SRC (x), 0);

      return 0;

    case AND:
    case IOR:
      /* We write NOR as (and (not A) (not B)), but if we don't have a NOR,
	 it is better to write this as (not (ior A B)) so we can split it.
	 Similarly for IOR.  */
      if (GET_CODE (XEXP (x, 0)) == NOT && GET_CODE (XEXP (x, 1)) == NOT)
	{
	  SUBST (*loc,
		 gen_rtx_NOT (GET_MODE (x),
			      gen_rtx_fmt_ee (code == IOR ? AND : IOR,
					      GET_MODE (x),
					      XEXP (XEXP (x, 0), 0),
					      XEXP (XEXP (x, 1), 0))));
	  return find_split_point (loc, insn, set_src);
	}

      /* Many RISC machines have a large set of logical insns.  If the
	 second operand is a NOT, put it first so we will try to split the
	 other operand first.  */
      if (GET_CODE (XEXP (x, 1)) == NOT)
	{
	  rtx tem = XEXP (x, 0);
	  SUBST (XEXP (x, 0), XEXP (x, 1));
	  SUBST (XEXP (x, 1), tem);
	}
      break;

    case PLUS:
    case MINUS:
      /* Canonicalization can produce (minus A (mult B C)), where C is a
	 constant.  It may be better to try splitting (plus (mult B -C) A)
	 instead if this isn't a multiply by a power of two.  */
      if (set_src && code == MINUS && GET_CODE (XEXP (x, 1)) == MULT
	  && GET_CODE (XEXP (XEXP (x, 1), 1)) == CONST_INT
	  && !pow2p_hwi (INTVAL (XEXP (XEXP (x, 1), 1))))
	{
	  machine_mode mode = GET_MODE (x);
	  unsigned HOST_WIDE_INT this_int = INTVAL (XEXP (XEXP (x, 1), 1));
	  HOST_WIDE_INT other_int = trunc_int_for_mode (-this_int, mode);
	  SUBST (*loc, gen_rtx_PLUS (mode,
				     gen_rtx_MULT (mode,
						   XEXP (XEXP (x, 1), 0),
						   gen_int_mode (other_int,
								 mode)),
				     XEXP (x, 0)));
	  return find_split_point (loc, insn, set_src);
	}

      /* Split at a multiply-accumulate instruction.  However if this is
         the SET_SRC, we likely do not have such an instruction and it's
         worthless to try this split.  */
      if (!set_src
	  && (GET_CODE (XEXP (x, 0)) == MULT
	      || (GET_CODE (XEXP (x, 0)) == ASHIFT
		  && GET_CODE (XEXP (XEXP (x, 0), 1)) == CONST_INT)))
        return loc;

    default:
      break;
    }

  /* Otherwise, select our actions depending on our rtx class.  */
  switch (GET_RTX_CLASS (code))
    {
    case RTX_BITFIELD_OPS:		/* This is ZERO_EXTRACT and SIGN_EXTRACT.  */
    case RTX_TERNARY:
      split = find_split_point (&XEXP (x, 2), insn, false);
      if (split)
	return split;
      /* fall through */
    case RTX_BIN_ARITH:
    case RTX_COMM_ARITH:
    case RTX_COMPARE:
    case RTX_COMM_COMPARE:
      split = find_split_point (&XEXP (x, 1), insn, false);
      if (split)
	return split;
      /* fall through */
    case RTX_UNARY:
      /* Some machines have (and (shift ...) ...) insns.  If X is not
	 an AND, but XEXP (X, 0) is, use it as our split point.  */
      if (GET_CODE (x) != AND && GET_CODE (XEXP (x, 0)) == AND)
	return &XEXP (x, 0);

      split = find_split_point (&XEXP (x, 0), insn, false);
      if (split)
	return split;
      return loc;

    default:
      /* Otherwise, we don't have a split point.  */
      return 0;
    }
}

/* Throughout X, replace FROM with TO, and return the result.
   The result is TO if X is FROM;
   otherwise the result is X, but its contents may have been modified.
   If they were modified, a record was made in undobuf so that
   undo_all will (among other things) return X to its original state.

   If the number of changes necessary is too much to record to undo,
   the excess changes are not made, so the result is invalid.
   The changes already made can still be undone.
   undobuf.num_undo is incremented for such changes, so by testing that
   the caller can tell whether the result is valid.

   `n_occurrences' is incremented each time FROM is replaced.

   IN_DEST is nonzero if we are processing the SET_DEST of a SET.

   IN_COND is nonzero if we are at the top level of a condition.

   UNIQUE_COPY is nonzero if each substitution must be unique.  We do this
   by copying if `n_occurrences' is nonzero.  */

static rtx
subst (rtx x, rtx from, rtx to, int in_dest, int in_cond, int unique_copy)
{
  enum rtx_code code = GET_CODE (x);
  machine_mode op0_mode = VOIDmode;
  const char *fmt;
  int len, i;
  rtx new_rtx;

/* Two expressions are equal if they are identical copies of a shared
   RTX or if they are both registers with the same register number
   and mode.  */

#define COMBINE_RTX_EQUAL_P(X,Y)			\
  ((X) == (Y)						\
   || (REG_P (X) && REG_P (Y)	\
       && REGNO (X) == REGNO (Y) && GET_MODE (X) == GET_MODE (Y)))

  /* Do not substitute into clobbers of regs -- this will never result in
     valid RTL.  */
  if (GET_CODE (x) == CLOBBER && REG_P (XEXP (x, 0)))
    return x;

  if (! in_dest && COMBINE_RTX_EQUAL_P (x, from))
    {
      n_occurrences++;
      return (unique_copy && n_occurrences > 1 ? copy_rtx (to) : to);
    }

  /* If X and FROM are the same register but different modes, they
     will not have been seen as equal above.  However, the log links code
     will make a LOG_LINKS entry for that case.  If we do nothing, we
     will try to rerecognize our original insn and, when it succeeds,
     we will delete the feeding insn, which is incorrect.

     So force this insn not to match in this (rare) case.  */
  if (! in_dest && code == REG && REG_P (from)
      && reg_overlap_mentioned_p (x, from))
    return gen_rtx_CLOBBER (GET_MODE (x), const0_rtx);

  /* If this is an object, we are done unless it is a MEM or LO_SUM, both
     of which may contain things that can be combined.  */
  if (code != MEM && code != LO_SUM && OBJECT_P (x))
    return x;

  /* It is possible to have a subexpression appear twice in the insn.
     Suppose that FROM is a register that appears within TO.
     Then, after that subexpression has been scanned once by `subst',
     the second time it is scanned, TO may be found.  If we were
     to scan TO here, we would find FROM within it and create a
     self-referent rtl structure which is completely wrong.  */
  if (COMBINE_RTX_EQUAL_P (x, to))
    return to;

  /* Parallel asm_operands need special attention because all of the
     inputs are shared across the arms.  Furthermore, unsharing the
     rtl results in recognition failures.  Failure to handle this case
     specially can result in circular rtl.

     Solve this by doing a normal pass across the first entry of the
     parallel, and only processing the SET_DESTs of the subsequent
     entries.  Ug.  */

  if (code == PARALLEL
      && GET_CODE (XVECEXP (x, 0, 0)) == SET
      && GET_CODE (SET_SRC (XVECEXP (x, 0, 0))) == ASM_OPERANDS)
    {
      new_rtx = subst (XVECEXP (x, 0, 0), from, to, 0, 0, unique_copy);

      /* If this substitution failed, this whole thing fails.  */
      if (GET_CODE (new_rtx) == CLOBBER
	  && XEXP (new_rtx, 0) == const0_rtx)
	return new_rtx;

      SUBST (XVECEXP (x, 0, 0), new_rtx);

      for (i = XVECLEN (x, 0) - 1; i >= 1; i--)
	{
	  rtx dest = SET_DEST (XVECEXP (x, 0, i));

	  if (!REG_P (dest)
	      && GET_CODE (dest) != CC0
	      && GET_CODE (dest) != PC)
	    {
	      new_rtx = subst (dest, from, to, 0, 0, unique_copy);

	      /* If this substitution failed, this whole thing fails.  */
	      if (GET_CODE (new_rtx) == CLOBBER
		  && XEXP (new_rtx, 0) == const0_rtx)
		return new_rtx;

	      SUBST (SET_DEST (XVECEXP (x, 0, i)), new_rtx);
	    }
	}
    }
  else
    {
      len = GET_RTX_LENGTH (code);
      fmt = GET_RTX_FORMAT (code);

      /* We don't need to process a SET_DEST that is a register, CC0,
	 or PC, so set up to skip this common case.  All other cases
	 where we want to suppress replacing something inside a
	 SET_SRC are handled via the IN_DEST operand.  */
      if (code == SET
	  && (REG_P (SET_DEST (x))
	      || GET_CODE (SET_DEST (x)) == CC0
	      || GET_CODE (SET_DEST (x)) == PC))
	fmt = "ie";

      /* Trying to simplify the operands of a widening MULT is not likely
	 to create RTL matching a machine insn.  */
      if (code == MULT
	  && (GET_CODE (XEXP (x, 0)) == ZERO_EXTEND
	      || GET_CODE (XEXP (x, 0)) == SIGN_EXTEND)
	  && (GET_CODE (XEXP (x, 1)) == ZERO_EXTEND
	      || GET_CODE (XEXP (x, 1)) == SIGN_EXTEND)
	  && REG_P (XEXP (XEXP (x, 0), 0))
	  && REG_P (XEXP (XEXP (x, 1), 0))
	  && from == to)
	return x;


      /* Get the mode of operand 0 in case X is now a SIGN_EXTEND of a
	 constant.  */
      if (fmt[0] == 'e')
	op0_mode = GET_MODE (XEXP (x, 0));

      for (i = 0; i < len; i++)
	{
	  if (fmt[i] == 'E')
	    {
	      int j;
	      for (j = XVECLEN (x, i) - 1; j >= 0; j--)
		{
		  if (COMBINE_RTX_EQUAL_P (XVECEXP (x, i, j), from))
		    {
		      new_rtx = (unique_copy && n_occurrences
			     ? copy_rtx (to) : to);
		      n_occurrences++;
		    }
		  else
		    {
		      new_rtx = subst (XVECEXP (x, i, j), from, to, 0, 0,
				       unique_copy);

		      /* If this substitution failed, this whole thing
			 fails.  */
		      if (GET_CODE (new_rtx) == CLOBBER
			  && XEXP (new_rtx, 0) == const0_rtx)
			return new_rtx;
		    }

		  SUBST (XVECEXP (x, i, j), new_rtx);
		}
	    }
	  else if (fmt[i] == 'e')
	    {
	      /* If this is a register being set, ignore it.  */
	      new_rtx = XEXP (x, i);
	      if (in_dest
		  && i == 0
		  && (((code == SUBREG || code == ZERO_EXTRACT)
		       && REG_P (new_rtx))
		      || code == STRICT_LOW_PART))
		;

	      else if (COMBINE_RTX_EQUAL_P (XEXP (x, i), from))
		{
		  /* In general, don't install a subreg involving two
		     modes not tieable.  It can worsen register
		     allocation, and can even make invalid reload
		     insns, since the reg inside may need to be copied
		     from in the outside mode, and that may be invalid
		     if it is an fp reg copied in integer mode.

		     We allow two exceptions to this: It is valid if
		     it is inside another SUBREG and the mode of that
		     SUBREG and the mode of the inside of TO is
		     tieable and it is valid if X is a SET that copies
		     FROM to CC0.  */

		  if (GET_CODE (to) == SUBREG
		      && !targetm.modes_tieable_p (GET_MODE (to),
						   GET_MODE (SUBREG_REG (to)))
		      && ! (code == SUBREG
			    && (targetm.modes_tieable_p
				(GET_MODE (x), GET_MODE (SUBREG_REG (to)))))
		      && (!HAVE_cc0
			  || (! (code == SET
				 && i == 1
				 && XEXP (x, 0) == cc0_rtx))))
		    return gen_rtx_CLOBBER (VOIDmode, const0_rtx);

		  if (code == SUBREG
		      && REG_P (to)
		      && REGNO (to) < FIRST_PSEUDO_REGISTER
		      && simplify_subreg_regno (REGNO (to), GET_MODE (to),
						SUBREG_BYTE (x),
						GET_MODE (x)) < 0)
		    return gen_rtx_CLOBBER (VOIDmode, const0_rtx);

		  new_rtx = (unique_copy && n_occurrences ? copy_rtx (to) : to);
		  n_occurrences++;
		}
	      else
		/* If we are in a SET_DEST, suppress most cases unless we
		   have gone inside a MEM, in which case we want to
		   simplify the address.  We assume here that things that
		   are actually part of the destination have their inner
		   parts in the first expression.  This is true for SUBREG,
		   STRICT_LOW_PART, and ZERO_EXTRACT, which are the only
		   things aside from REG and MEM that should appear in a
		   SET_DEST.  */
		new_rtx = subst (XEXP (x, i), from, to,
			     (((in_dest
				&& (code == SUBREG || code == STRICT_LOW_PART
				    || code == ZERO_EXTRACT))
			       || code == SET)
			      && i == 0),
				 code == IF_THEN_ELSE && i == 0,
				 unique_copy);

	      /* If we found that we will have to reject this combination,
		 indicate that by returning the CLOBBER ourselves, rather than
		 an expression containing it.  This will speed things up as
		 well as prevent accidents where two CLOBBERs are considered
		 to be equal, thus producing an incorrect simplification.  */

	      if (GET_CODE (new_rtx) == CLOBBER && XEXP (new_rtx, 0) == const0_rtx)
		return new_rtx;

	      if (GET_CODE (x) == SUBREG && CONST_SCALAR_INT_P (new_rtx))
		{
		  machine_mode mode = GET_MODE (x);

		  x = simplify_subreg (GET_MODE (x), new_rtx,
				       GET_MODE (SUBREG_REG (x)),
				       SUBREG_BYTE (x));
		  if (! x)
		    x = gen_rtx_CLOBBER (mode, const0_rtx);
		}
	      else if (CONST_SCALAR_INT_P (new_rtx)
		       && (GET_CODE (x) == ZERO_EXTEND
			   || GET_CODE (x) == FLOAT
			   || GET_CODE (x) == UNSIGNED_FLOAT))
		{
		  x = simplify_unary_operation (GET_CODE (x), GET_MODE (x),
						new_rtx,
						GET_MODE (XEXP (x, 0)));
		  if (!x)
		    return gen_rtx_CLOBBER (VOIDmode, const0_rtx);
		}
	      else
		SUBST (XEXP (x, i), new_rtx);
	    }
	}
    }

  /* Check if we are loading something from the constant pool via float
     extension; in this case we would undo compress_float_constant
     optimization and degenerate constant load to an immediate value.  */
  if (GET_CODE (x) == FLOAT_EXTEND
      && MEM_P (XEXP (x, 0))
      && MEM_READONLY_P (XEXP (x, 0)))
    {
      rtx tmp = avoid_constant_pool_reference (x);
      if (x != tmp)
        return x;
    }

  /* Try to simplify X.  If the simplification changed the code, it is likely
     that further simplification will help, so loop, but limit the number
     of repetitions that will be performed.  */

  for (i = 0; i < 4; i++)
    {
      /* If X is sufficiently simple, don't bother trying to do anything
	 with it.  */
      if (code != CONST_INT && code != REG && code != CLOBBER)
	x = combine_simplify_rtx (x, op0_mode, in_dest, in_cond);

      if (GET_CODE (x) == code)
	break;

      code = GET_CODE (x);

      /* We no longer know the original mode of operand 0 since we
	 have changed the form of X)  */
      op0_mode = VOIDmode;
    }

  return x;
}

/* If X is a commutative operation whose operands are not in the canonical
   order, use substitutions to swap them.  */

static void
maybe_swap_commutative_operands (rtx x)
{
  if (COMMUTATIVE_ARITH_P (x)
      && swap_commutative_operands_p (XEXP (x, 0), XEXP (x, 1)))
    {
      rtx temp = XEXP (x, 0);
      SUBST (XEXP (x, 0), XEXP (x, 1));
      SUBST (XEXP (x, 1), temp);
    }
}

/* Simplify X, a piece of RTL.  We just operate on the expression at the
   outer level; call `subst' to simplify recursively.  Return the new
   expression.

   OP0_MODE is the original mode of XEXP (x, 0).  IN_DEST is nonzero
   if we are inside a SET_DEST.  IN_COND is nonzero if we are at the top level
   of a condition.  */

static rtx
combine_simplify_rtx (rtx x, machine_mode op0_mode, int in_dest,
		      int in_cond)
{
  enum rtx_code code = GET_CODE (x);
  machine_mode mode = GET_MODE (x);
  scalar_int_mode int_mode;
  rtx temp;
  int i;

  /* If this is a commutative operation, put a constant last and a complex
     expression first.  We don't need to do this for comparisons here.  */
  maybe_swap_commutative_operands (x);

  /* Try to fold this expression in case we have constants that weren't
     present before.  */
  temp = 0;
  switch (GET_RTX_CLASS (code))
    {
    case RTX_UNARY:
      if (op0_mode == VOIDmode)
	op0_mode = GET_MODE (XEXP (x, 0));
      temp = simplify_unary_operation (code, mode, XEXP (x, 0), op0_mode);
      break;
    case RTX_COMPARE:
    case RTX_COMM_COMPARE:
      {
	machine_mode cmp_mode = GET_MODE (XEXP (x, 0));
	if (cmp_mode == VOIDmode)
	  {
	    cmp_mode = GET_MODE (XEXP (x, 1));
	    if (cmp_mode == VOIDmode)
	      cmp_mode = op0_mode;
	  }
	temp = simplify_relational_operation (code, mode, cmp_mode,
					      XEXP (x, 0), XEXP (x, 1));
      }
      break;
    case RTX_COMM_ARITH:
    case RTX_BIN_ARITH:
      temp = simplify_binary_operation (code, mode, XEXP (x, 0), XEXP (x, 1));
      break;
    case RTX_BITFIELD_OPS:
    case RTX_TERNARY:
      temp = simplify_ternary_operation (code, mode, op0_mode, XEXP (x, 0),
					 XEXP (x, 1), XEXP (x, 2));
      break;
    default:
      break;
    }

  if (temp)
    {
      x = temp;
      code = GET_CODE (temp);
      op0_mode = VOIDmode;
      mode = GET_MODE (temp);
    }

  /* If this is a simple operation applied to an IF_THEN_ELSE, try
     applying it to the arms of the IF_THEN_ELSE.  This often simplifies
     things.  Check for cases where both arms are testing the same
     condition.

     Don't do anything if all operands are very simple.  */

  if ((BINARY_P (x)
       && ((!OBJECT_P (XEXP (x, 0))
	    && ! (GET_CODE (XEXP (x, 0)) == SUBREG
		  && OBJECT_P (SUBREG_REG (XEXP (x, 0)))))
	   || (!OBJECT_P (XEXP (x, 1))
	       && ! (GET_CODE (XEXP (x, 1)) == SUBREG
		     && OBJECT_P (SUBREG_REG (XEXP (x, 1)))))))
      || (UNARY_P (x)
	  && (!OBJECT_P (XEXP (x, 0))
	       && ! (GET_CODE (XEXP (x, 0)) == SUBREG
		     && OBJECT_P (SUBREG_REG (XEXP (x, 0)))))))
    {
      rtx cond, true_rtx, false_rtx;

      cond = if_then_else_cond (x, &true_rtx, &false_rtx);
      if (cond != 0
	  /* If everything is a comparison, what we have is highly unlikely
	     to be simpler, so don't use it.  */
	  && ! (COMPARISON_P (x)
		&& (COMPARISON_P (true_rtx) || COMPARISON_P (false_rtx)))
	  /* Similarly, if we end up with one of the expressions the same
	     as the original, it is certainly not simpler.  */
	  && ! rtx_equal_p (x, true_rtx)
	  && ! rtx_equal_p (x, false_rtx))
	{
	  rtx cop1 = const0_rtx;
	  enum rtx_code cond_code = simplify_comparison (NE, &cond, &cop1);

	  if (cond_code == NE && COMPARISON_P (cond))
	    return x;

	  /* Simplify the alternative arms; this may collapse the true and
	     false arms to store-flag values.  Be careful to use copy_rtx
	     here since true_rtx or false_rtx might share RTL with x as a
	     result of the if_then_else_cond call above.  */
	  true_rtx = subst (copy_rtx (true_rtx), pc_rtx, pc_rtx, 0, 0, 0);
	  false_rtx = subst (copy_rtx (false_rtx), pc_rtx, pc_rtx, 0, 0, 0);

	  /* If true_rtx and false_rtx are not general_operands, an if_then_else
	     is unlikely to be simpler.  */
	  if (general_operand (true_rtx, VOIDmode)
	      && general_operand (false_rtx, VOIDmode))
	    {
	      enum rtx_code reversed;

	      /* Restarting if we generate a store-flag expression will cause
		 us to loop.  Just drop through in this case.  */

	      /* If the result values are STORE_FLAG_VALUE and zero, we can
		 just make the comparison operation.  */
	      if (true_rtx == const_true_rtx && false_rtx == const0_rtx)
		x = simplify_gen_relational (cond_code, mode, VOIDmode,
					     cond, cop1);
	      else if (true_rtx == const0_rtx && false_rtx == const_true_rtx
		       && ((reversed = reversed_comparison_code_parts
					(cond_code, cond, cop1, NULL))
			   != UNKNOWN))
		x = simplify_gen_relational (reversed, mode, VOIDmode,
					     cond, cop1);

	      /* Likewise, we can make the negate of a comparison operation
		 if the result values are - STORE_FLAG_VALUE and zero.  */
	      else if (CONST_INT_P (true_rtx)
		       && INTVAL (true_rtx) == - STORE_FLAG_VALUE
		       && false_rtx == const0_rtx)
		x = simplify_gen_unary (NEG, mode,
					simplify_gen_relational (cond_code,
								 mode, VOIDmode,
								 cond, cop1),
					mode);
	      else if (CONST_INT_P (false_rtx)
		       && INTVAL (false_rtx) == - STORE_FLAG_VALUE
		       && true_rtx == const0_rtx
		       && ((reversed = reversed_comparison_code_parts
					(cond_code, cond, cop1, NULL))
			   != UNKNOWN))
		x = simplify_gen_unary (NEG, mode,
					simplify_gen_relational (reversed,
								 mode, VOIDmode,
								 cond, cop1),
					mode);
	      else
		return gen_rtx_IF_THEN_ELSE (mode,
					     simplify_gen_relational (cond_code,
								      mode,
								      VOIDmode,
								      cond,
								      cop1),
					     true_rtx, false_rtx);

	      code = GET_CODE (x);
	      op0_mode = VOIDmode;
	    }
	}
    }

  /* First see if we can apply the inverse distributive law.  */
  if (code == PLUS || code == MINUS
      || code == AND || code == IOR || code == XOR)
    {
      x = apply_distributive_law (x);
      code = GET_CODE (x);
      op0_mode = VOIDmode;
    }

  /* If CODE is an associative operation not otherwise handled, see if we
     can associate some operands.  This can win if they are constants or
     if they are logically related (i.e. (a & b) & a).  */
  if ((code == PLUS || code == MINUS || code == MULT || code == DIV
       || code == AND || code == IOR || code == XOR
       || code == SMAX || code == SMIN || code == UMAX || code == UMIN)
      && ((INTEGRAL_MODE_P (mode) && code != DIV)
	  || (flag_associative_math && FLOAT_MODE_P (mode))))
    {
      if (GET_CODE (XEXP (x, 0)) == code)
	{
	  rtx other = XEXP (XEXP (x, 0), 0);
	  rtx inner_op0 = XEXP (XEXP (x, 0), 1);
	  rtx inner_op1 = XEXP (x, 1);
	  rtx inner;

	  /* Make sure we pass the constant operand if any as the second
	     one if this is a commutative operation.  */
	  if (CONSTANT_P (inner_op0) && COMMUTATIVE_ARITH_P (x))
	    std::swap (inner_op0, inner_op1);
	  inner = simplify_binary_operation (code == MINUS ? PLUS
					     : code == DIV ? MULT
					     : code,
					     mode, inner_op0, inner_op1);

	  /* For commutative operations, try the other pair if that one
	     didn't simplify.  */
	  if (inner == 0 && COMMUTATIVE_ARITH_P (x))
	    {
	      other = XEXP (XEXP (x, 0), 1);
	      inner = simplify_binary_operation (code, mode,
						 XEXP (XEXP (x, 0), 0),
						 XEXP (x, 1));
	    }

	  if (inner)
	    return simplify_gen_binary (code, mode, other, inner);
	}
    }

  /* A little bit of algebraic simplification here.  */
  switch (code)
    {
    case MEM:
      /* Ensure that our address has any ASHIFTs converted to MULT in case
	 address-recognizing predicates are called later.  */
      temp = make_compound_operation (XEXP (x, 0), MEM);
      SUBST (XEXP (x, 0), temp);
      break;

    case SUBREG:
      if (op0_mode == VOIDmode)
	op0_mode = GET_MODE (SUBREG_REG (x));

      /* See if this can be moved to simplify_subreg.  */
      if (CONSTANT_P (SUBREG_REG (x))
	  && known_eq (subreg_lowpart_offset (mode, op0_mode), SUBREG_BYTE (x))
	     /* Don't call gen_lowpart if the inner mode
		is VOIDmode and we cannot simplify it, as SUBREG without
		inner mode is invalid.  */
	  && (GET_MODE (SUBREG_REG (x)) != VOIDmode
	      || gen_lowpart_common (mode, SUBREG_REG (x))))
	return gen_lowpart (mode, SUBREG_REG (x));

      if (GET_MODE_CLASS (GET_MODE (SUBREG_REG (x))) == MODE_CC)
	break;
      {
	rtx temp;
	temp = simplify_subreg (mode, SUBREG_REG (x), op0_mode,
				SUBREG_BYTE (x));
	if (temp)
	  return temp;

	/* If op is known to have all lower bits zero, the result is zero.  */
	scalar_int_mode int_mode, int_op0_mode;
	if (!in_dest
	    && is_a <scalar_int_mode> (mode, &int_mode)
	    && is_a <scalar_int_mode> (op0_mode, &int_op0_mode)
	    && (GET_MODE_PRECISION (int_mode)
		< GET_MODE_PRECISION (int_op0_mode))
	    && known_eq (subreg_lowpart_offset (int_mode, int_op0_mode),
			 SUBREG_BYTE (x))
	    && HWI_COMPUTABLE_MODE_P (int_op0_mode)
	    && (nonzero_bits (SUBREG_REG (x), int_op0_mode)
		& GET_MODE_MASK (int_mode)) == 0)
	  return CONST0_RTX (int_mode);
      }

      /* Don't change the mode of the MEM if that would change the meaning
	 of the address.  */
      if (MEM_P (SUBREG_REG (x))
	  && (MEM_VOLATILE_P (SUBREG_REG (x))
	      || mode_dependent_address_p (XEXP (SUBREG_REG (x), 0),
					   MEM_ADDR_SPACE (SUBREG_REG (x)))))
	return gen_rtx_CLOBBER (mode, const0_rtx);

      /* Note that we cannot do any narrowing for non-constants since
	 we might have been counting on using the fact that some bits were
	 zero.  We now do this in the SET.  */

      break;

    case NEG:
      temp = expand_compound_operation (XEXP (x, 0));

      /* For C equal to the width of MODE minus 1, (neg (ashiftrt X C)) can be
	 replaced by (lshiftrt X C).  This will convert
	 (neg (sign_extract X 1 Y)) to (zero_extract X 1 Y).  */

      if (GET_CODE (temp) == ASHIFTRT
	  && CONST_INT_P (XEXP (temp, 1))
	  && INTVAL (XEXP (temp, 1)) == GET_MODE_UNIT_PRECISION (mode) - 1)
	return simplify_shift_const (NULL_RTX, LSHIFTRT, mode, XEXP (temp, 0),
				     INTVAL (XEXP (temp, 1)));

      /* If X has only a single bit that might be nonzero, say, bit I, convert
	 (neg X) to (ashiftrt (ashift X C-I) C-I) where C is the bitsize of
	 MODE minus 1.  This will convert (neg (zero_extract X 1 Y)) to
	 (sign_extract X 1 Y).  But only do this if TEMP isn't a register
	 or a SUBREG of one since we'd be making the expression more
	 complex if it was just a register.  */

      if (!REG_P (temp)
	  && ! (GET_CODE (temp) == SUBREG
		&& REG_P (SUBREG_REG (temp)))
	  && is_a <scalar_int_mode> (mode, &int_mode)
	  && (i = exact_log2 (nonzero_bits (temp, int_mode))) >= 0)
	{
	  rtx temp1 = simplify_shift_const
	    (NULL_RTX, ASHIFTRT, int_mode,
	     simplify_shift_const (NULL_RTX, ASHIFT, int_mode, temp,
				   GET_MODE_PRECISION (int_mode) - 1 - i),
	     GET_MODE_PRECISION (int_mode) - 1 - i);

	  /* If all we did was surround TEMP with the two shifts, we
	     haven't improved anything, so don't use it.  Otherwise,
	     we are better off with TEMP1.  */
	  if (GET_CODE (temp1) != ASHIFTRT
	      || GET_CODE (XEXP (temp1, 0)) != ASHIFT
	      || XEXP (XEXP (temp1, 0), 0) != temp)
	    return temp1;
	}
      break;

    case TRUNCATE:
      /* We can't handle truncation to a partial integer mode here
	 because we don't know the real bitsize of the partial
	 integer mode.  */
      if (GET_MODE_CLASS (mode) == MODE_PARTIAL_INT)
	break;

      if (HWI_COMPUTABLE_MODE_P (mode))
	SUBST (XEXP (x, 0),
	       force_to_mode (XEXP (x, 0), GET_MODE (XEXP (x, 0)),
			      GET_MODE_MASK (mode), 0));

      /* We can truncate a constant value and return it.  */
      {
	poly_int64 c;
	if (poly_int_rtx_p (XEXP (x, 0), &c))
	  return gen_int_mode (c, mode);
      }

      /* Similarly to what we do in simplify-rtx.c, a truncate of a register
	 whose value is a comparison can be replaced with a subreg if
	 STORE_FLAG_VALUE permits.  */
      if (HWI_COMPUTABLE_MODE_P (mode)
	  && (STORE_FLAG_VALUE & ~GET_MODE_MASK (mode)) == 0
	  && (temp = get_last_value (XEXP (x, 0)))
	  && COMPARISON_P (temp))
	return gen_lowpart (mode, XEXP (x, 0));
      break;

    case CONST:
      /* (const (const X)) can become (const X).  Do it this way rather than
	 returning the inner CONST since CONST can be shared with a
	 REG_EQUAL note.  */
      if (GET_CODE (XEXP (x, 0)) == CONST)
	SUBST (XEXP (x, 0), XEXP (XEXP (x, 0), 0));
      break;

    case LO_SUM:
      /* Convert (lo_sum (high FOO) FOO) to FOO.  This is necessary so we
	 can add in an offset.  find_split_point will split this address up
	 again if it doesn't match.  */
      if (HAVE_lo_sum && GET_CODE (XEXP (x, 0)) == HIGH
	  && rtx_equal_p (XEXP (XEXP (x, 0), 0), XEXP (x, 1)))
	return XEXP (x, 1);
      break;

    case PLUS:
      /* (plus (xor (and <foo> (const_int pow2 - 1)) <c>) <-c>)
	 when c is (const_int (pow2 + 1) / 2) is a sign extension of a
	 bit-field and can be replaced by either a sign_extend or a
	 sign_extract.  The `and' may be a zero_extend and the two
	 <c>, -<c> constants may be reversed.  */
      if (GET_CODE (XEXP (x, 0)) == XOR
	  && is_a <scalar_int_mode> (mode, &int_mode)
	  && CONST_INT_P (XEXP (x, 1))
	  && CONST_INT_P (XEXP (XEXP (x, 0), 1))
	  && INTVAL (XEXP (x, 1)) == -INTVAL (XEXP (XEXP (x, 0), 1))
	  && ((i = exact_log2 (UINTVAL (XEXP (XEXP (x, 0), 1)))) >= 0
	      || (i = exact_log2 (UINTVAL (XEXP (x, 1)))) >= 0)
	  && HWI_COMPUTABLE_MODE_P (int_mode)
	  && ((GET_CODE (XEXP (XEXP (x, 0), 0)) == AND
	       && CONST_INT_P (XEXP (XEXP (XEXP (x, 0), 0), 1))
	       && (UINTVAL (XEXP (XEXP (XEXP (x, 0), 0), 1))
		   == (HOST_WIDE_INT_1U << (i + 1)) - 1))
	      || (GET_CODE (XEXP (XEXP (x, 0), 0)) == ZERO_EXTEND
		  && known_eq ((GET_MODE_PRECISION
				(GET_MODE (XEXP (XEXP (XEXP (x, 0), 0), 0)))),
			       (unsigned int) i + 1))))
	return simplify_shift_const
	  (NULL_RTX, ASHIFTRT, int_mode,
	   simplify_shift_const (NULL_RTX, ASHIFT, int_mode,
				 XEXP (XEXP (XEXP (x, 0), 0), 0),
				 GET_MODE_PRECISION (int_mode) - (i + 1)),
	   GET_MODE_PRECISION (int_mode) - (i + 1));

      /* If only the low-order bit of X is possibly nonzero, (plus x -1)
	 can become (ashiftrt (ashift (xor x 1) C) C) where C is
	 the bitsize of the mode - 1.  This allows simplification of
	 "a = (b & 8) == 0;"  */
      if (XEXP (x, 1) == constm1_rtx
	  && !REG_P (XEXP (x, 0))
	  && ! (GET_CODE (XEXP (x, 0)) == SUBREG
		&& REG_P (SUBREG_REG (XEXP (x, 0))))
	  && is_a <scalar_int_mode> (mode, &int_mode)
	  && nonzero_bits (XEXP (x, 0), int_mode) == 1)
	return simplify_shift_const
	  (NULL_RTX, ASHIFTRT, int_mode,
	   simplify_shift_const (NULL_RTX, ASHIFT, int_mode,
				 gen_rtx_XOR (int_mode, XEXP (x, 0),
					      const1_rtx),
				 GET_MODE_PRECISION (int_mode) - 1),
	   GET_MODE_PRECISION (int_mode) - 1);

      /* If we are adding two things that have no bits in common, convert
	 the addition into an IOR.  This will often be further simplified,
	 for example in cases like ((a & 1) + (a & 2)), which can
	 become a & 3.  */

      if (HWI_COMPUTABLE_MODE_P (mode)
	  && (nonzero_bits (XEXP (x, 0), mode)
	      & nonzero_bits (XEXP (x, 1), mode)) == 0)
	{
	  /* Try to simplify the expression further.  */
	  rtx tor = simplify_gen_binary (IOR, mode, XEXP (x, 0), XEXP (x, 1));
	  temp = combine_simplify_rtx (tor, VOIDmode, in_dest, 0);

	  /* If we could, great.  If not, do not go ahead with the IOR
	     replacement, since PLUS appears in many special purpose
	     address arithmetic instructions.  */
	  if (GET_CODE (temp) != CLOBBER
	      && (GET_CODE (temp) != IOR
		  || ((XEXP (temp, 0) != XEXP (x, 0)
		       || XEXP (temp, 1) != XEXP (x, 1))
		      && (XEXP (temp, 0) != XEXP (x, 1)
			  || XEXP (temp, 1) != XEXP (x, 0)))))
	    return temp;
	}

      /* Canonicalize x + x into x << 1.  */
      if (GET_MODE_CLASS (mode) == MODE_INT
	  && rtx_equal_p (XEXP (x, 0), XEXP (x, 1))
	  && !side_effects_p (XEXP (x, 0)))
	return simplify_gen_binary (ASHIFT, mode, XEXP (x, 0), const1_rtx);

      break;

    case MINUS:
      /* (minus <foo> (and <foo> (const_int -pow2))) becomes
	 (and <foo> (const_int pow2-1))  */
      if (is_a <scalar_int_mode> (mode, &int_mode)
	  && GET_CODE (XEXP (x, 1)) == AND
	  && CONST_INT_P (XEXP (XEXP (x, 1), 1))
	  && pow2p_hwi (-UINTVAL (XEXP (XEXP (x, 1), 1)))
	  && rtx_equal_p (XEXP (XEXP (x, 1), 0), XEXP (x, 0)))
	return simplify_and_const_int (NULL_RTX, int_mode, XEXP (x, 0),
				       -INTVAL (XEXP (XEXP (x, 1), 1)) - 1);
      break;

    case MULT:
      /* If we have (mult (plus A B) C), apply the distributive law and then
	 the inverse distributive law to see if things simplify.  This
	 occurs mostly in addresses, often when unrolling loops.  */

      if (GET_CODE (XEXP (x, 0)) == PLUS)
	{
	  rtx result = distribute_and_simplify_rtx (x, 0);
	  if (result)
	    return result;
	}

      /* Try simplify a*(b/c) as (a*b)/c.  */
      if (FLOAT_MODE_P (mode) && flag_associative_math
	  && GET_CODE (XEXP (x, 0)) == DIV)
	{
	  rtx tem = simplify_binary_operation (MULT, mode,
					       XEXP (XEXP (x, 0), 0),
					       XEXP (x, 1));
	  if (tem)
	    return simplify_gen_binary (DIV, mode, tem, XEXP (XEXP (x, 0), 1));
	}
      break;

    case UDIV:
      /* If this is a divide by a power of two, treat it as a shift if
	 its first operand is a shift.  */
      if (is_a <scalar_int_mode> (mode, &int_mode)
	  && CONST_INT_P (XEXP (x, 1))
	  && (i = exact_log2 (UINTVAL (XEXP (x, 1)))) >= 0
	  && (GET_CODE (XEXP (x, 0)) == ASHIFT
	      || GET_CODE (XEXP (x, 0)) == LSHIFTRT
	      || GET_CODE (XEXP (x, 0)) == ASHIFTRT
	      || GET_CODE (XEXP (x, 0)) == ROTATE
	      || GET_CODE (XEXP (x, 0)) == ROTATERT))
	return simplify_shift_const (NULL_RTX, LSHIFTRT, int_mode,
				     XEXP (x, 0), i);
      break;

    case EQ:  case NE:
    case GT:  case GTU:  case GE:  case GEU:
    case LT:  case LTU:  case LE:  case LEU:
    case UNEQ:  case LTGT:
    case UNGT:  case UNGE:
    case UNLT:  case UNLE:
    case UNORDERED: case ORDERED:
      /* If the first operand is a condition code, we can't do anything
	 with it.  */
      if (GET_CODE (XEXP (x, 0)) == COMPARE
	  || (GET_MODE_CLASS (GET_MODE (XEXP (x, 0))) != MODE_CC
	      && ! CC0_P (XEXP (x, 0))))
	{
	  rtx op0 = XEXP (x, 0);
	  rtx op1 = XEXP (x, 1);
	  enum rtx_code new_code;

	  if (GET_CODE (op0) == COMPARE)
	    op1 = XEXP (op0, 1), op0 = XEXP (op0, 0);

	  /* Simplify our comparison, if possible.  */
	  new_code = simplify_comparison (code, &op0, &op1);

	  /* If STORE_FLAG_VALUE is 1, we can convert (ne x 0) to simply X
	     if only the low-order bit is possibly nonzero in X (such as when
	     X is a ZERO_EXTRACT of one bit).  Similarly, we can convert EQ to
	     (xor X 1) or (minus 1 X); we use the former.  Finally, if X is
	     known to be either 0 or -1, NE becomes a NEG and EQ becomes
	     (plus X 1).

	     Remove any ZERO_EXTRACT we made when thinking this was a
	     comparison.  It may now be simpler to use, e.g., an AND.  If a
	     ZERO_EXTRACT is indeed appropriate, it will be placed back by
	     the call to make_compound_operation in the SET case.

	     Don't apply these optimizations if the caller would
	     prefer a comparison rather than a value.
	     E.g., for the condition in an IF_THEN_ELSE most targets need
	     an explicit comparison.  */

	  if (in_cond)
	    ;

	  else if (STORE_FLAG_VALUE == 1
		   && new_code == NE
		   && is_int_mode (mode, &int_mode)
		   && op1 == const0_rtx
		   && int_mode == GET_MODE (op0)
		   && nonzero_bits (op0, int_mode) == 1)
	    return gen_lowpart (int_mode,
				expand_compound_operation (op0));

	  else if (STORE_FLAG_VALUE == 1
		   && new_code == NE
		   && is_int_mode (mode, &int_mode)
		   && op1 == const0_rtx
		   && int_mode == GET_MODE (op0)
		   && (num_sign_bit_copies (op0, int_mode)
		       == GET_MODE_PRECISION (int_mode)))
	    {
	      op0 = expand_compound_operation (op0);
	      return simplify_gen_unary (NEG, int_mode,
					 gen_lowpart (int_mode, op0),
					 int_mode);
	    }

	  else if (STORE_FLAG_VALUE == 1
		   && new_code == EQ
		   && is_int_mode (mode, &int_mode)
		   && op1 == const0_rtx
		   && int_mode == GET_MODE (op0)
		   && nonzero_bits (op0, int_mode) == 1)
	    {
	      op0 = expand_compound_operation (op0);
	      return simplify_gen_binary (XOR, int_mode,
					  gen_lowpart (int_mode, op0),
					  const1_rtx);
	    }

	  else if (STORE_FLAG_VALUE == 1
		   && new_code == EQ
		   && is_int_mode (mode, &int_mode)
		   && op1 == const0_rtx
		   && int_mode == GET_MODE (op0)
		   && (num_sign_bit_copies (op0, int_mode)
		       == GET_MODE_PRECISION (int_mode)))
	    {
	      op0 = expand_compound_operation (op0);
	      return plus_constant (int_mode, gen_lowpart (int_mode, op0), 1);
	    }

	  /* If STORE_FLAG_VALUE is -1, we have cases similar to
	     those above.  */
	  if (in_cond)
	    ;

	  else if (STORE_FLAG_VALUE == -1
		   && new_code == NE
		   && is_int_mode (mode, &int_mode)
		   && op1 == const0_rtx
		   && int_mode == GET_MODE (op0)
		   && (num_sign_bit_copies (op0, int_mode)
		       == GET_MODE_PRECISION (int_mode)))
	    return gen_lowpart (int_mode, expand_compound_operation (op0));

	  else if (STORE_FLAG_VALUE == -1
		   && new_code == NE
		   && is_int_mode (mode, &int_mode)
		   && op1 == const0_rtx
		   && int_mode == GET_MODE (op0)
		   && nonzero_bits (op0, int_mode) == 1)
	    {
	      op0 = expand_compound_operation (op0);
	      return simplify_gen_unary (NEG, int_mode,
					 gen_lowpart (int_mode, op0),
					 int_mode);
	    }

	  else if (STORE_FLAG_VALUE == -1
		   && new_code == EQ
		   && is_int_mode (mode, &int_mode)
		   && op1 == const0_rtx
		   && int_mode == GET_MODE (op0)
		   && (num_sign_bit_copies (op0, int_mode)
		       == GET_MODE_PRECISION (int_mode)))
	    {
	      op0 = expand_compound_operation (op0);
	      return simplify_gen_unary (NOT, int_mode,
					 gen_lowpart (int_mode, op0),
					 int_mode);
	    }

	  /* If X is 0/1, (eq X 0) is X-1.  */
	  else if (STORE_FLAG_VALUE == -1
		   && new_code == EQ
		   && is_int_mode (mode, &int_mode)
		   && op1 == const0_rtx
		   && int_mode == GET_MODE (op0)
		   && nonzero_bits (op0, int_mode) == 1)
	    {
	      op0 = expand_compound_operation (op0);
	      return plus_constant (int_mode, gen_lowpart (int_mode, op0), -1);
	    }

	  /* If STORE_FLAG_VALUE says to just test the sign bit and X has just
	     one bit that might be nonzero, we can convert (ne x 0) to
	     (ashift x c) where C puts the bit in the sign bit.  Remove any
	     AND with STORE_FLAG_VALUE when we are done, since we are only
	     going to test the sign bit.  */
	  if (new_code == NE
	      && is_int_mode (mode, &int_mode)
	      && HWI_COMPUTABLE_MODE_P (int_mode)
	      && val_signbit_p (int_mode, STORE_FLAG_VALUE)
	      && op1 == const0_rtx
	      && int_mode == GET_MODE (op0)
	      && (i = exact_log2 (nonzero_bits (op0, int_mode))) >= 0)
	    {
	      x = simplify_shift_const (NULL_RTX, ASHIFT, int_mode,
					expand_compound_operation (op0),
					GET_MODE_PRECISION (int_mode) - 1 - i);
	      if (GET_CODE (x) == AND && XEXP (x, 1) == const_true_rtx)
		return XEXP (x, 0);
	      else
		return x;
	    }

	  /* If the code changed, return a whole new comparison.
	     We also need to avoid using SUBST in cases where
	     simplify_comparison has widened a comparison with a CONST_INT,
	     since in that case the wider CONST_INT may fail the sanity
	     checks in do_SUBST.  */
	  if (new_code != code
	      || (CONST_INT_P (op1)
		  && GET_MODE (op0) != GET_MODE (XEXP (x, 0))
		  && GET_MODE (op0) != GET_MODE (XEXP (x, 1))))
	    return gen_rtx_fmt_ee (new_code, mode, op0, op1);

	  /* Otherwise, keep this operation, but maybe change its operands.
	     This also converts (ne (compare FOO BAR) 0) to (ne FOO BAR).  */
	  SUBST (XEXP (x, 0), op0);
	  SUBST (XEXP (x, 1), op1);
	}
      break;

    case IF_THEN_ELSE:
      return simplify_if_then_else (x);

    case ZERO_EXTRACT:
    case SIGN_EXTRACT:
    case ZERO_EXTEND:
    case SIGN_EXTEND:
      /* If we are processing SET_DEST, we are done.  */
      if (in_dest)
	return x;

      return expand_compound_operation (x);

    case SET:
      return simplify_set (x);

    case AND:
    case IOR:
      return simplify_logical (x);

    case ASHIFT:
    case LSHIFTRT:
    case ASHIFTRT:
    case ROTATE:
    case ROTATERT:
      /* If this is a shift by a constant amount, simplify it.  */
      if (CONST_INT_P (XEXP (x, 1)))
	return simplify_shift_const (x, code, mode, XEXP (x, 0),
				     INTVAL (XEXP (x, 1)));

      else if (SHIFT_COUNT_TRUNCATED && !REG_P (XEXP (x, 1)))
	SUBST (XEXP (x, 1),
	       force_to_mode (XEXP (x, 1), GET_MODE (XEXP (x, 1)),
			      (HOST_WIDE_INT_1U
			       << exact_log2 (GET_MODE_UNIT_BITSIZE
					      (GET_MODE (x))))
			      - 1,
			      0));
      break;

    default:
      break;
    }

  return x;
}

/* Simplify X, an IF_THEN_ELSE expression.  Return the new expression.  */

static rtx
simplify_if_then_else (rtx x)
{
  machine_mode mode = GET_MODE (x);
  rtx cond = XEXP (x, 0);
  rtx true_rtx = XEXP (x, 1);
  rtx false_rtx = XEXP (x, 2);
  enum rtx_code true_code = GET_CODE (cond);
  int comparison_p = COMPARISON_P (cond);
  rtx temp;
  int i;
  enum rtx_code false_code;
  rtx reversed;
  scalar_int_mode int_mode, inner_mode;

  /* Simplify storing of the truth value.  */
  if (comparison_p && true_rtx == const_true_rtx && false_rtx == const0_rtx)
    return simplify_gen_relational (true_code, mode, VOIDmode,
				    XEXP (cond, 0), XEXP (cond, 1));

  /* Also when the truth value has to be reversed.  */
  if (comparison_p
      && true_rtx == const0_rtx && false_rtx == const_true_rtx
      && (reversed = reversed_comparison (cond, mode)))
    return reversed;

  /* Sometimes we can simplify the arm of an IF_THEN_ELSE if a register used
     in it is being compared against certain values.  Get the true and false
     comparisons and see if that says anything about the value of each arm.  */

  if (comparison_p
      && ((false_code = reversed_comparison_code (cond, NULL))
	  != UNKNOWN)
      && REG_P (XEXP (cond, 0)))
    {
      HOST_WIDE_INT nzb;
      rtx from = XEXP (cond, 0);
      rtx true_val = XEXP (cond, 1);
      rtx false_val = true_val;
      int swapped = 0;

      /* If FALSE_CODE is EQ, swap the codes and arms.  */

      if (false_code == EQ)
	{
	  swapped = 1, true_code = EQ, false_code = NE;
	  std::swap (true_rtx, false_rtx);
	}

      scalar_int_mode from_mode;
      if (is_a <scalar_int_mode> (GET_MODE (from), &from_mode))
	{
	  /* If we are comparing against zero and the expression being
	     tested has only a single bit that might be nonzero, that is
	     its value when it is not equal to zero.  Similarly if it is
	     known to be -1 or 0.  */
	  if (true_code == EQ
	      && true_val == const0_rtx
	      && pow2p_hwi (nzb = nonzero_bits (from, from_mode)))
	    {
	      false_code = EQ;
	      false_val = gen_int_mode (nzb, from_mode);
	    }
	  else if (true_code == EQ
		   && true_val == const0_rtx
		   && (num_sign_bit_copies (from, from_mode)
		       == GET_MODE_PRECISION (from_mode)))
	    {
	      false_code = EQ;
	      false_val = constm1_rtx;
	    }
	}

      /* Now simplify an arm if we know the value of the register in the
	 branch and it is used in the arm.  Be careful due to the potential
	 of locally-shared RTL.  */

      if (reg_mentioned_p (from, true_rtx))
	true_rtx = subst (known_cond (copy_rtx (true_rtx), true_code,
				      from, true_val),
			  pc_rtx, pc_rtx, 0, 0, 0);
      if (reg_mentioned_p (from, false_rtx))
	false_rtx = subst (known_cond (copy_rtx (false_rtx), false_code,
				       from, false_val),
			   pc_rtx, pc_rtx, 0, 0, 0);

      SUBST (XEXP (x, 1), swapped ? false_rtx : true_rtx);
      SUBST (XEXP (x, 2), swapped ? true_rtx : false_rtx);

      true_rtx = XEXP (x, 1);
      false_rtx = XEXP (x, 2);
      true_code = GET_CODE (cond);
    }

  /* If we have (if_then_else FOO (pc) (label_ref BAR)) and FOO can be
     reversed, do so to avoid needing two sets of patterns for
     subtract-and-branch insns.  Similarly if we have a constant in the true
     arm, the false arm is the same as the first operand of the comparison, or
     the false arm is more complicated than the true arm.  */

  if (comparison_p
      && reversed_comparison_code (cond, NULL) != UNKNOWN
      && (true_rtx == pc_rtx
	  || (CONSTANT_P (true_rtx)
	      && !CONST_INT_P (false_rtx) && false_rtx != pc_rtx)
	  || true_rtx == const0_rtx
	  || (OBJECT_P (true_rtx) && !OBJECT_P (false_rtx))
	  || (GET_CODE (true_rtx) == SUBREG && OBJECT_P (SUBREG_REG (true_rtx))
	      && !OBJECT_P (false_rtx))
	  || reg_mentioned_p (true_rtx, false_rtx)
	  || rtx_equal_p (false_rtx, XEXP (cond, 0))))
    {
      true_code = reversed_comparison_code (cond, NULL);
      SUBST (XEXP (x, 0), reversed_comparison (cond, GET_MODE (cond)));
      SUBST (XEXP (x, 1), false_rtx);
      SUBST (XEXP (x, 2), true_rtx);

      std::swap (true_rtx, false_rtx);
      cond = XEXP (x, 0);

      /* It is possible that the conditional has been simplified out.  */
      true_code = GET_CODE (cond);
      comparison_p = COMPARISON_P (cond);
    }

  /* If the two arms are identical, we don't need the comparison.  */

  if (rtx_equal_p (true_rtx, false_rtx) && ! side_effects_p (cond))
    return true_rtx;

  /* Convert a == b ? b : a to "a".  */
  if (true_code == EQ && ! side_effects_p (cond)
      && !HONOR_NANS (mode)
      && rtx_equal_p (XEXP (cond, 0), false_rtx)
      && rtx_equal_p (XEXP (cond, 1), true_rtx))
    return false_rtx;
  else if (true_code == NE && ! side_effects_p (cond)
	   && !HONOR_NANS (mode)
	   && rtx_equal_p (XEXP (cond, 0), true_rtx)
	   && rtx_equal_p (XEXP (cond, 1), false_rtx))
    return true_rtx;

  /* Look for cases where we have (abs x) or (neg (abs X)).  */

  if (GET_MODE_CLASS (mode) == MODE_INT
      && comparison_p
      && XEXP (cond, 1) == const0_rtx
      && GET_CODE (false_rtx) == NEG
      && rtx_equal_p (true_rtx, XEXP (false_rtx, 0))
      && rtx_equal_p (true_rtx, XEXP (cond, 0))
      && ! side_effects_p (true_rtx))
    switch (true_code)
      {
      case GT:
      case GE:
	return simplify_gen_unary (ABS, mode, true_rtx, mode);
      case LT:
      case LE:
	return
	  simplify_gen_unary (NEG, mode,
			      simplify_gen_unary (ABS, mode, true_rtx, mode),
			      mode);
      default:
	break;
      }

  /* Look for MIN or MAX.  */

  if ((! FLOAT_MODE_P (mode) || flag_unsafe_math_optimizations)
      && comparison_p
      && rtx_equal_p (XEXP (cond, 0), true_rtx)
      && rtx_equal_p (XEXP (cond, 1), false_rtx)
      && ! side_effects_p (cond))
    switch (true_code)
      {
      case GE:
      case GT:
	return simplify_gen_binary (SMAX, mode, true_rtx, false_rtx);
      case LE:
      case LT:
	return simplify_gen_binary (SMIN, mode, true_rtx, false_rtx);
      case GEU:
      case GTU:
	return simplify_gen_binary (UMAX, mode, true_rtx, false_rtx);
      case LEU:
      case LTU:
	return simplify_gen_binary (UMIN, mode, true_rtx, false_rtx);
      default:
	break;
      }

  /* If we have (if_then_else COND (OP Z C1) Z) and OP is an identity when its
     second operand is zero, this can be done as (OP Z (mult COND C2)) where
     C2 = C1 * STORE_FLAG_VALUE. Similarly if OP has an outer ZERO_EXTEND or
     SIGN_EXTEND as long as Z is already extended (so we don't destroy it).
     We can do this kind of thing in some cases when STORE_FLAG_VALUE is
     neither 1 or -1, but it isn't worth checking for.  */

  if ((STORE_FLAG_VALUE == 1 || STORE_FLAG_VALUE == -1)
      && comparison_p
      && is_int_mode (mode, &int_mode)
      && ! side_effects_p (x))
    {
      rtx t = make_compound_operation (true_rtx, SET);
      rtx f = make_compound_operation (false_rtx, SET);
      rtx cond_op0 = XEXP (cond, 0);
      rtx cond_op1 = XEXP (cond, 1);
      enum rtx_code op = UNKNOWN, extend_op = UNKNOWN;
      scalar_int_mode m = int_mode;
      rtx z = 0, c1 = NULL_RTX;

      if ((GET_CODE (t) == PLUS || GET_CODE (t) == MINUS
	   || GET_CODE (t) == IOR || GET_CODE (t) == XOR
	   || GET_CODE (t) == ASHIFT
	   || GET_CODE (t) == LSHIFTRT || GET_CODE (t) == ASHIFTRT)
	  && rtx_equal_p (XEXP (t, 0), f))
	c1 = XEXP (t, 1), op = GET_CODE (t), z = f;

      /* If an identity-zero op is commutative, check whether there
	 would be a match if we swapped the operands.  */
      else if ((GET_CODE (t) == PLUS || GET_CODE (t) == IOR
		|| GET_CODE (t) == XOR)
	       && rtx_equal_p (XEXP (t, 1), f))
	c1 = XEXP (t, 0), op = GET_CODE (t), z = f;
      else if (GET_CODE (t) == SIGN_EXTEND
	       && is_a <scalar_int_mode> (GET_MODE (XEXP (t, 0)), &inner_mode)
	       && (GET_CODE (XEXP (t, 0)) == PLUS
		   || GET_CODE (XEXP (t, 0)) == MINUS
		   || GET_CODE (XEXP (t, 0)) == IOR
		   || GET_CODE (XEXP (t, 0)) == XOR
		   || GET_CODE (XEXP (t, 0)) == ASHIFT
		   || GET_CODE (XEXP (t, 0)) == LSHIFTRT
		   || GET_CODE (XEXP (t, 0)) == ASHIFTRT)
	       && GET_CODE (XEXP (XEXP (t, 0), 0)) == SUBREG
	       && subreg_lowpart_p (XEXP (XEXP (t, 0), 0))
	       && rtx_equal_p (SUBREG_REG (XEXP (XEXP (t, 0), 0)), f)
	       && (num_sign_bit_copies (f, GET_MODE (f))
		   > (unsigned int)
		     (GET_MODE_PRECISION (int_mode)
		      - GET_MODE_PRECISION (inner_mode))))
	{
	  c1 = XEXP (XEXP (t, 0), 1); z = f; op = GET_CODE (XEXP (t, 0));
	  extend_op = SIGN_EXTEND;
	  m = inner_mode;
	}
      else if (GET_CODE (t) == SIGN_EXTEND
	       && is_a <scalar_int_mode> (GET_MODE (XEXP (t, 0)), &inner_mode)
	       && (GET_CODE (XEXP (t, 0)) == PLUS
		   || GET_CODE (XEXP (t, 0)) == IOR
		   || GET_CODE (XEXP (t, 0)) == XOR)
	       && GET_CODE (XEXP (XEXP (t, 0), 1)) == SUBREG
	       && subreg_lowpart_p (XEXP (XEXP (t, 0), 1))
	       && rtx_equal_p (SUBREG_REG (XEXP (XEXP (t, 0), 1)), f)
	       && (num_sign_bit_copies (f, GET_MODE (f))
		   > (unsigned int)
		     (GET_MODE_PRECISION (int_mode)
		      - GET_MODE_PRECISION (inner_mode))))
	{
	  c1 = XEXP (XEXP (t, 0), 0); z = f; op = GET_CODE (XEXP (t, 0));
	  extend_op = SIGN_EXTEND;
	  m = inner_mode;
	}
      else if (GET_CODE (t) == ZERO_EXTEND
	       && is_a <scalar_int_mode> (GET_MODE (XEXP (t, 0)), &inner_mode)
	       && (GET_CODE (XEXP (t, 0)) == PLUS
		   || GET_CODE (XEXP (t, 0)) == MINUS
		   || GET_CODE (XEXP (t, 0)) == IOR
		   || GET_CODE (XEXP (t, 0)) == XOR
		   || GET_CODE (XEXP (t, 0)) == ASHIFT
		   || GET_CODE (XEXP (t, 0)) == LSHIFTRT
		   || GET_CODE (XEXP (t, 0)) == ASHIFTRT)
	       && GET_CODE (XEXP (XEXP (t, 0), 0)) == SUBREG
	       && HWI_COMPUTABLE_MODE_P (int_mode)
	       && subreg_lowpart_p (XEXP (XEXP (t, 0), 0))
	       && rtx_equal_p (SUBREG_REG (XEXP (XEXP (t, 0), 0)), f)
	       && ((nonzero_bits (f, GET_MODE (f))
		    & ~GET_MODE_MASK (inner_mode))
		   == 0))
	{
	  c1 = XEXP (XEXP (t, 0), 1); z = f; op = GET_CODE (XEXP (t, 0));
	  extend_op = ZERO_EXTEND;
	  m = inner_mode;
	}
      else if (GET_CODE (t) == ZERO_EXTEND
	       && is_a <scalar_int_mode> (GET_MODE (XEXP (t, 0)), &inner_mode)
	       && (GET_CODE (XEXP (t, 0)) == PLUS
		   || GET_CODE (XEXP (t, 0)) == IOR
		   || GET_CODE (XEXP (t, 0)) == XOR)
	       && GET_CODE (XEXP (XEXP (t, 0), 1)) == SUBREG
	       && HWI_COMPUTABLE_MODE_P (int_mode)
	       && subreg_lowpart_p (XEXP (XEXP (t, 0), 1))
	       && rtx_equal_p (SUBREG_REG (XEXP (XEXP (t, 0), 1)), f)
	       && ((nonzero_bits (f, GET_MODE (f))
		    & ~GET_MODE_MASK (inner_mode))
		   == 0))
	{
	  c1 = XEXP (XEXP (t, 0), 0); z = f; op = GET_CODE (XEXP (t, 0));
	  extend_op = ZERO_EXTEND;
	  m = inner_mode;
	}

      if (z)
	{
	  machine_mode cm = m;
	  if ((op == ASHIFT || op == LSHIFTRT || op == ASHIFTRT)
	      && GET_MODE (c1) != VOIDmode)
	    cm = GET_MODE (c1);
	  temp = subst (simplify_gen_relational (true_code, cm, VOIDmode,
						 cond_op0, cond_op1),
			pc_rtx, pc_rtx, 0, 0, 0);
	  temp = simplify_gen_binary (MULT, cm, temp,
				      simplify_gen_binary (MULT, cm, c1,
							   const_true_rtx));
	  temp = subst (temp, pc_rtx, pc_rtx, 0, 0, 0);
	  temp = simplify_gen_binary (op, m, gen_lowpart (m, z), temp);

	  if (extend_op != UNKNOWN)
	    temp = simplify_gen_unary (extend_op, int_mode, temp, m);

	  return temp;
	}
    }

  /* If we have (if_then_else (ne A 0) C1 0) and either A is known to be 0 or
     1 and C1 is a single bit or A is known to be 0 or -1 and C1 is the
     negation of a single bit, we can convert this operation to a shift.  We
     can actually do this more generally, but it doesn't seem worth it.  */

  if (true_code == NE
      && is_a <scalar_int_mode> (mode, &int_mode)
      && XEXP (cond, 1) == const0_rtx
      && false_rtx == const0_rtx
      && CONST_INT_P (true_rtx)
      && ((nonzero_bits (XEXP (cond, 0), int_mode) == 1
	   && (i = exact_log2 (UINTVAL (true_rtx))) >= 0)
	  || ((num_sign_bit_copies (XEXP (cond, 0), int_mode)
	       == GET_MODE_PRECISION (int_mode))
	      && (i = exact_log2 (-UINTVAL (true_rtx))) >= 0)))
    return
      simplify_shift_const (NULL_RTX, ASHIFT, int_mode,
			    gen_lowpart (int_mode, XEXP (cond, 0)), i);

  /* (IF_THEN_ELSE (NE A 0) C1 0) is A or a zero-extend of A if the only
     non-zero bit in A is C1.  */
  if (true_code == NE && XEXP (cond, 1) == const0_rtx
      && false_rtx == const0_rtx && CONST_INT_P (true_rtx)
      && is_a <scalar_int_mode> (mode, &int_mode)
      && is_a <scalar_int_mode> (GET_MODE (XEXP (cond, 0)), &inner_mode)
      && (UINTVAL (true_rtx) & GET_MODE_MASK (int_mode))
	  == nonzero_bits (XEXP (cond, 0), inner_mode)
      && (i = exact_log2 (UINTVAL (true_rtx) & GET_MODE_MASK (int_mode))) >= 0)
    {
      rtx val = XEXP (cond, 0);
      if (inner_mode == int_mode)
        return val;
      else if (GET_MODE_PRECISION (inner_mode) < GET_MODE_PRECISION (int_mode))
        return simplify_gen_unary (ZERO_EXTEND, int_mode, val, inner_mode);
    }

  return x;
}

/* Simplify X, a SET expression.  Return the new expression.  */

static rtx
simplify_set (rtx x)
{
  rtx src = SET_SRC (x);
  rtx dest = SET_DEST (x);
  machine_mode mode
    = GET_MODE (src) != VOIDmode ? GET_MODE (src) : GET_MODE (dest);
  rtx_insn *other_insn;
  rtx *cc_use;
  scalar_int_mode int_mode;

  /* (set (pc) (return)) gets written as (return).  */
  if (GET_CODE (dest) == PC && ANY_RETURN_P (src))
    return src;

  /* Now that we know for sure which bits of SRC we are using, see if we can
     simplify the expression for the object knowing that we only need the
     low-order bits.  */

  if (GET_MODE_CLASS (mode) == MODE_INT && HWI_COMPUTABLE_MODE_P (mode))
    {
      src = force_to_mode (src, mode, HOST_WIDE_INT_M1U, 0);
      SUBST (SET_SRC (x), src);
    }

  /* If we are setting CC0 or if the source is a COMPARE, look for the use of
     the comparison result and try to simplify it unless we already have used
     undobuf.other_insn.  */
  if ((GET_MODE_CLASS (mode) == MODE_CC
       || GET_CODE (src) == COMPARE
       || CC0_P (dest))
      && (cc_use = find_single_use (dest, subst_insn, &other_insn)) != 0
      && (undobuf.other_insn == 0 || other_insn == undobuf.other_insn)
      && COMPARISON_P (*cc_use)
      && rtx_equal_p (XEXP (*cc_use, 0), dest))
    {
      enum rtx_code old_code = GET_CODE (*cc_use);
      enum rtx_code new_code;
      rtx op0, op1, tmp;
      int other_changed = 0;
      rtx inner_compare = NULL_RTX;
      machine_mode compare_mode = GET_MODE (dest);

      if (GET_CODE (src) == COMPARE)
	{
	  op0 = XEXP (src, 0), op1 = XEXP (src, 1);
	  if (GET_CODE (op0) == COMPARE && op1 == const0_rtx)
	    {
	      inner_compare = op0;
	      op0 = XEXP (inner_compare, 0), op1 = XEXP (inner_compare, 1);
	    }
	}
      else
	op0 = src, op1 = CONST0_RTX (GET_MODE (src));

      tmp = simplify_relational_operation (old_code, compare_mode, VOIDmode,
					   op0, op1);
      if (!tmp)
	new_code = old_code;
      else if (!CONSTANT_P (tmp))
	{
	  new_code = GET_CODE (tmp);
	  op0 = XEXP (tmp, 0);
	  op1 = XEXP (tmp, 1);
	}
      else
	{
	  rtx pat = PATTERN (other_insn);
	  undobuf.other_insn = other_insn;
	  SUBST (*cc_use, tmp);

	  /* Attempt to simplify CC user.  */
	  if (GET_CODE (pat) == SET)
	    {
	      rtx new_rtx = simplify_rtx (SET_SRC (pat));
	      if (new_rtx != NULL_RTX)
		SUBST (SET_SRC (pat), new_rtx);
	    }

	  /* Convert X into a no-op move.  */
	  SUBST (SET_DEST (x), pc_rtx);
	  SUBST (SET_SRC (x), pc_rtx);
	  return x;
	}

      /* Simplify our comparison, if possible.  */
      new_code = simplify_comparison (new_code, &op0, &op1);

#ifdef SELECT_CC_MODE
      /* If this machine has CC modes other than CCmode, check to see if we
	 need to use a different CC mode here.  */
      if (GET_MODE_CLASS (GET_MODE (op0)) == MODE_CC)
	compare_mode = GET_MODE (op0);
      else if (inner_compare
	       && GET_MODE_CLASS (GET_MODE (inner_compare)) == MODE_CC
	       && new_code == old_code
	       && op0 == XEXP (inner_compare, 0)
	       && op1 == XEXP (inner_compare, 1))
	compare_mode = GET_MODE (inner_compare);
      else
	compare_mode = SELECT_CC_MODE (new_code, op0, op1);

      /* If the mode changed, we have to change SET_DEST, the mode in the
	 compare, and the mode in the place SET_DEST is used.  If SET_DEST is
	 a hard register, just build new versions with the proper mode.  If it
	 is a pseudo, we lose unless it is only time we set the pseudo, in
	 which case we can safely change its mode.  */
      if (!HAVE_cc0 && compare_mode != GET_MODE (dest))
	{
	  if (can_change_dest_mode (dest, 0, compare_mode))
	    {
	      unsigned int regno = REGNO (dest);
	      rtx new_dest;

	      if (regno < FIRST_PSEUDO_REGISTER)
		new_dest = gen_rtx_REG (compare_mode, regno);
	      else
		{
		  SUBST_MODE (regno_reg_rtx[regno], compare_mode);
		  new_dest = regno_reg_rtx[regno];
		}

	      SUBST (SET_DEST (x), new_dest);
	      SUBST (XEXP (*cc_use, 0), new_dest);
	      other_changed = 1;

	      dest = new_dest;
	    }
	}
#endif  /* SELECT_CC_MODE */

      /* If the code changed, we have to build a new comparison in
	 undobuf.other_insn.  */
      if (new_code != old_code)
	{
	  int other_changed_previously = other_changed;
	  unsigned HOST_WIDE_INT mask;
	  rtx old_cc_use = *cc_use;

	  SUBST (*cc_use, gen_rtx_fmt_ee (new_code, GET_MODE (*cc_use),
					  dest, const0_rtx));
	  other_changed = 1;

	  /* If the only change we made was to change an EQ into an NE or
	     vice versa, OP0 has only one bit that might be nonzero, and OP1
	     is zero, check if changing the user of the condition code will
	     produce a valid insn.  If it won't, we can keep the original code
	     in that insn by surrounding our operation with an XOR.  */

	  if (((old_code == NE && new_code == EQ)
	       || (old_code == EQ && new_code == NE))
	      && ! other_changed_previously && op1 == const0_rtx
	      && HWI_COMPUTABLE_MODE_P (GET_MODE (op0))
	      && pow2p_hwi (mask = nonzero_bits (op0, GET_MODE (op0))))
	    {
	      rtx pat = PATTERN (other_insn), note = 0;

	      if ((recog_for_combine (&pat, other_insn, &note) < 0
		   && ! check_asm_operands (pat)))
		{
		  *cc_use = old_cc_use;
		  other_changed = 0;

		  op0 = simplify_gen_binary (XOR, GET_MODE (op0), op0,
					     gen_int_mode (mask,
							   GET_MODE (op0)));
		}
	    }
	}

      if (other_changed)
	undobuf.other_insn = other_insn;

      /* Don't generate a compare of a CC with 0, just use that CC.  */
      if (GET_MODE (op0) == compare_mode && op1 == const0_rtx)
	{
	  SUBST (SET_SRC (x), op0);
	  src = SET_SRC (x);
	}
      /* Otherwise, if we didn't previously have the same COMPARE we
	 want, create it from scratch.  */
      else if (GET_CODE (src) != COMPARE || GET_MODE (src) != compare_mode
	       || XEXP (src, 0) != op0 || XEXP (src, 1) != op1)
	{
	  SUBST (SET_SRC (x), gen_rtx_COMPARE (compare_mode, op0, op1));
	  src = SET_SRC (x);
	}
    }
  else
    {
      /* Get SET_SRC in a form where we have placed back any
	 compound expressions.  Then do the checks below.  */
      src = make_compound_operation (src, SET);
      SUBST (SET_SRC (x), src);
    }

  /* If we have (set x (subreg:m1 (op:m2 ...) 0)) with OP being some operation,
     and X being a REG or (subreg (reg)), we may be able to convert this to
     (set (subreg:m2 x) (op)).

     We can always do this if M1 is narrower than M2 because that means that
     we only care about the low bits of the result.

     However, on machines without WORD_REGISTER_OPERATIONS defined, we cannot
     perform a narrower operation than requested since the high-order bits will
     be undefined.  On machine where it is defined, this transformation is safe
     as long as M1 and M2 have the same number of words.  */

  if (GET_CODE (src) == SUBREG && subreg_lowpart_p (src)
      && !OBJECT_P (SUBREG_REG (src))
      && (known_equal_after_align_up
	  (GET_MODE_SIZE (GET_MODE (src)),
	   GET_MODE_SIZE (GET_MODE (SUBREG_REG (src))),
	   UNITS_PER_WORD))
      && (WORD_REGISTER_OPERATIONS || !paradoxical_subreg_p (src))
      && ! (REG_P (dest) && REGNO (dest) < FIRST_PSEUDO_REGISTER
	    && !REG_CAN_CHANGE_MODE_P (REGNO (dest),
				       GET_MODE (SUBREG_REG (src)),
				       GET_MODE (src)))
      && (REG_P (dest)
	  || (GET_CODE (dest) == SUBREG
	      && REG_P (SUBREG_REG (dest)))))
    {
      SUBST (SET_DEST (x),
	     gen_lowpart (GET_MODE (SUBREG_REG (src)),
				      dest));
      SUBST (SET_SRC (x), SUBREG_REG (src));

      src = SET_SRC (x), dest = SET_DEST (x);
    }

  /* If we have (set (cc0) (subreg ...)), we try to remove the subreg
     in SRC.  */
  if (dest == cc0_rtx
      && partial_subreg_p (src)
      && subreg_lowpart_p (src))
    {
      rtx inner = SUBREG_REG (src);
      machine_mode inner_mode = GET_MODE (inner);

      /* Here we make sure that we don't have a sign bit on.  */
      if (val_signbit_known_clear_p (GET_MODE (src),
				     nonzero_bits (inner, inner_mode)))
	{
	  SUBST (SET_SRC (x), inner);
	  src = SET_SRC (x);
	}
    }

  /* If we have (set FOO (subreg:M (mem:N BAR) 0)) with M wider than N, this
     would require a paradoxical subreg.  Replace the subreg with a
     zero_extend to avoid the reload that would otherwise be required.
     Don't do this unless we have a scalar integer mode, otherwise the
     transformation is incorrect.  */

  enum rtx_code extend_op;
  if (paradoxical_subreg_p (src)
      && MEM_P (SUBREG_REG (src))
      && SCALAR_INT_MODE_P (GET_MODE (src))
      && (extend_op = load_extend_op (GET_MODE (SUBREG_REG (src)))) != UNKNOWN)
    {
      SUBST (SET_SRC (x),
	     gen_rtx_fmt_e (extend_op, GET_MODE (src), SUBREG_REG (src)));

      src = SET_SRC (x);
    }

  /* If we don't have a conditional move, SET_SRC is an IF_THEN_ELSE, and we
     are comparing an item known to be 0 or -1 against 0, use a logical
     operation instead. Check for one of the arms being an IOR of the other
     arm with some value.  We compute three terms to be IOR'ed together.  In
     practice, at most two will be nonzero.  Then we do the IOR's.  */

  if (GET_CODE (dest) != PC
      && GET_CODE (src) == IF_THEN_ELSE
      && is_int_mode (GET_MODE (src), &int_mode)
      && (GET_CODE (XEXP (src, 0)) == EQ || GET_CODE (XEXP (src, 0)) == NE)
      && XEXP (XEXP (src, 0), 1) == const0_rtx
      && int_mode == GET_MODE (XEXP (XEXP (src, 0), 0))
      && (!HAVE_conditional_move
	  || ! can_conditionally_move_p (int_mode))
      && (num_sign_bit_copies (XEXP (XEXP (src, 0), 0), int_mode)
	  == GET_MODE_PRECISION (int_mode))
      && ! side_effects_p (src))
    {
      rtx true_rtx = (GET_CODE (XEXP (src, 0)) == NE
		      ? XEXP (src, 1) : XEXP (src, 2));
      rtx false_rtx = (GET_CODE (XEXP (src, 0)) == NE
		   ? XEXP (src, 2) : XEXP (src, 1));
      rtx term1 = const0_rtx, term2, term3;

      if (GET_CODE (true_rtx) == IOR
	  && rtx_equal_p (XEXP (true_rtx, 0), false_rtx))
	term1 = false_rtx, true_rtx = XEXP (true_rtx, 1), false_rtx = const0_rtx;
      else if (GET_CODE (true_rtx) == IOR
	       && rtx_equal_p (XEXP (true_rtx, 1), false_rtx))
	term1 = false_rtx, true_rtx = XEXP (true_rtx, 0), false_rtx = const0_rtx;
      else if (GET_CODE (false_rtx) == IOR
	       && rtx_equal_p (XEXP (false_rtx, 0), true_rtx))
	term1 = true_rtx, false_rtx = XEXP (false_rtx, 1), true_rtx = const0_rtx;
      else if (GET_CODE (false_rtx) == IOR
	       && rtx_equal_p (XEXP (false_rtx, 1), true_rtx))
	term1 = true_rtx, false_rtx = XEXP (false_rtx, 0), true_rtx = const0_rtx;

      term2 = simplify_gen_binary (AND, int_mode,
				   XEXP (XEXP (src, 0), 0), true_rtx);
      term3 = simplify_gen_binary (AND, int_mode,
				   simplify_gen_unary (NOT, int_mode,
						       XEXP (XEXP (src, 0), 0),
						       int_mode),
				   false_rtx);

      SUBST (SET_SRC (x),
	     simplify_gen_binary (IOR, int_mode,
				  simplify_gen_binary (IOR, int_mode,
						       term1, term2),
				  term3));

      src = SET_SRC (x);
    }

  /* If either SRC or DEST is a CLOBBER of (const_int 0), make this
     whole thing fail.  */
  if (GET_CODE (src) == CLOBBER && XEXP (src, 0) == const0_rtx)
    return src;
  else if (GET_CODE (dest) == CLOBBER && XEXP (dest, 0) == const0_rtx)
    return dest;
  else
    /* Convert this into a field assignment operation, if possible.  */
    return make_field_assignment (x);
}

/* Simplify, X, and AND, IOR, or XOR operation, and return the simplified
   result.  */

static rtx
simplify_logical (rtx x)
{
  rtx op0 = XEXP (x, 0);
  rtx op1 = XEXP (x, 1);
  scalar_int_mode mode;

  switch (GET_CODE (x))
    {
    case AND:
      /* We can call simplify_and_const_int only if we don't lose
	 any (sign) bits when converting INTVAL (op1) to
	 "unsigned HOST_WIDE_INT".  */
      if (is_a <scalar_int_mode> (GET_MODE (x), &mode)
	  && CONST_INT_P (op1)
	  && (HWI_COMPUTABLE_MODE_P (mode)
	      || INTVAL (op1) > 0))
	{
	  x = simplify_and_const_int (x, mode, op0, INTVAL (op1));
	  if (GET_CODE (x) != AND)
	    return x;

	  op0 = XEXP (x, 0);
	  op1 = XEXP (x, 1);
	}

      /* If we have any of (and (ior A B) C) or (and (xor A B) C),
	 apply the distributive law and then the inverse distributive
	 law to see if things simplify.  */
      if (GET_CODE (op0) == IOR || GET_CODE (op0) == XOR)
	{
	  rtx result = distribute_and_simplify_rtx (x, 0);
	  if (result)
	    return result;
	}
      if (GET_CODE (op1) == IOR || GET_CODE (op1) == XOR)
	{
	  rtx result = distribute_and_simplify_rtx (x, 1);
	  if (result)
	    return result;
	}
      break;

    case IOR:
      /* If we have (ior (and A B) C), apply the distributive law and then
	 the inverse distributive law to see if things simplify.  */

      if (GET_CODE (op0) == AND)
	{
	  rtx result = distribute_and_simplify_rtx (x, 0);
	  if (result)
	    return result;
	}

      if (GET_CODE (op1) == AND)
	{
	  rtx result = distribute_and_simplify_rtx (x, 1);
	  if (result)
	    return result;
	}
      break;

    default:
      gcc_unreachable ();
    }

  return x;
}

/* We consider ZERO_EXTRACT, SIGN_EXTRACT, and SIGN_EXTEND as "compound
   operations" because they can be replaced with two more basic operations.
   ZERO_EXTEND is also considered "compound" because it can be replaced with
   an AND operation, which is simpler, though only one operation.

   The function expand_compound_operation is called with an rtx expression
   and will convert it to the appropriate shifts and AND operations,
   simplifying at each stage.

   The function make_compound_operation is called to convert an expression
   consisting of shifts and ANDs into the equivalent compound expression.
   It is the inverse of this function, loosely speaking.  */

static rtx
expand_compound_operation (rtx x)
{
  unsigned HOST_WIDE_INT pos = 0, len;
  int unsignedp = 0;
  unsigned int modewidth;
  rtx tem;
  scalar_int_mode inner_mode;

  switch (GET_CODE (x))
    {
    case ZERO_EXTEND:
      unsignedp = 1;
      /* FALLTHRU */
    case SIGN_EXTEND:
      /* We can't necessarily use a const_int for a multiword mode;
	 it depends on implicitly extending the value.
	 Since we don't know the right way to extend it,
	 we can't tell whether the implicit way is right.

	 Even for a mode that is no wider than a const_int,
	 we can't win, because we need to sign extend one of its bits through
	 the rest of it, and we don't know which bit.  */
      if (CONST_INT_P (XEXP (x, 0)))
	return x;

      /* Reject modes that aren't scalar integers because turning vector
	 or complex modes into shifts causes problems.  */
      if (!is_a <scalar_int_mode> (GET_MODE (XEXP (x, 0)), &inner_mode))
	return x;

      /* Return if (subreg:MODE FROM 0) is not a safe replacement for
	 (zero_extend:MODE FROM) or (sign_extend:MODE FROM).  It is for any MEM
	 because (SUBREG (MEM...)) is guaranteed to cause the MEM to be
	 reloaded. If not for that, MEM's would very rarely be safe.

	 Reject modes bigger than a word, because we might not be able
	 to reference a two-register group starting with an arbitrary register
	 (and currently gen_lowpart might crash for a SUBREG).  */

      if (GET_MODE_SIZE (inner_mode) > UNITS_PER_WORD)
	return x;

      len = GET_MODE_PRECISION (inner_mode);
      /* If the inner object has VOIDmode (the only way this can happen
	 is if it is an ASM_OPERANDS), we can't do anything since we don't
	 know how much masking to do.  */
      if (len == 0)
	return x;

      break;

    case ZERO_EXTRACT:
      unsignedp = 1;

      /* fall through */

    case SIGN_EXTRACT:
      /* If the operand is a CLOBBER, just return it.  */
      if (GET_CODE (XEXP (x, 0)) == CLOBBER)
	return XEXP (x, 0);

      if (!CONST_INT_P (XEXP (x, 1))
	  || !CONST_INT_P (XEXP (x, 2)))
	return x;

      /* Reject modes that aren't scalar integers because turning vector
	 or complex modes into shifts causes problems.  */
      if (!is_a <scalar_int_mode> (GET_MODE (XEXP (x, 0)), &inner_mode))
	return x;

      len = INTVAL (XEXP (x, 1));
      pos = INTVAL (XEXP (x, 2));

      /* This should stay within the object being extracted, fail otherwise.  */
      if (len + pos > GET_MODE_PRECISION (inner_mode))
	return x;

      if (BITS_BIG_ENDIAN)
	pos = GET_MODE_PRECISION (inner_mode) - len - pos;

      break;

    default:
      return x;
    }

  /* We've rejected non-scalar operations by now.  */
  scalar_int_mode mode = as_a <scalar_int_mode> (GET_MODE (x));

  /* Convert sign extension to zero extension, if we know that the high
     bit is not set, as this is easier to optimize.  It will be converted
     back to cheaper alternative in make_extraction.  */
  if (GET_CODE (x) == SIGN_EXTEND
      && HWI_COMPUTABLE_MODE_P (mode)
      && ((nonzero_bits (XEXP (x, 0), inner_mode)
	   & ~(((unsigned HOST_WIDE_INT) GET_MODE_MASK (inner_mode)) >> 1))
	  == 0))
    {
      rtx temp = gen_rtx_ZERO_EXTEND (mode, XEXP (x, 0));
      rtx temp2 = expand_compound_operation (temp);

      /* Make sure this is a profitable operation.  */
      if (set_src_cost (x, mode, optimize_this_for_speed_p)
          > set_src_cost (temp2, mode, optimize_this_for_speed_p))
       return temp2;
      else if (set_src_cost (x, mode, optimize_this_for_speed_p)
               > set_src_cost (temp, mode, optimize_this_for_speed_p))
       return temp;
      else
       return x;
    }

  /* We can optimize some special cases of ZERO_EXTEND.  */
  if (GET_CODE (x) == ZERO_EXTEND)
    {
      /* (zero_extend:DI (truncate:SI foo:DI)) is just foo:DI if we
	 know that the last value didn't have any inappropriate bits
	 set.  */
      if (GET_CODE (XEXP (x, 0)) == TRUNCATE
	  && GET_MODE (XEXP (XEXP (x, 0), 0)) == mode
	  && HWI_COMPUTABLE_MODE_P (mode)
	  && (nonzero_bits (XEXP (XEXP (x, 0), 0), mode)
	      & ~GET_MODE_MASK (inner_mode)) == 0)
	return XEXP (XEXP (x, 0), 0);

      /* Likewise for (zero_extend:DI (subreg:SI foo:DI 0)).  */
      if (GET_CODE (XEXP (x, 0)) == SUBREG
	  && GET_MODE (SUBREG_REG (XEXP (x, 0))) == mode
	  && subreg_lowpart_p (XEXP (x, 0))
	  && HWI_COMPUTABLE_MODE_P (mode)
	  && (nonzero_bits (SUBREG_REG (XEXP (x, 0)), mode)
	      & ~GET_MODE_MASK (inner_mode)) == 0)
	return SUBREG_REG (XEXP (x, 0));

      /* (zero_extend:DI (truncate:SI foo:DI)) is just foo:DI when foo
	 is a comparison and STORE_FLAG_VALUE permits.  This is like
	 the first case, but it works even when MODE is larger
	 than HOST_WIDE_INT.  */
      if (GET_CODE (XEXP (x, 0)) == TRUNCATE
	  && GET_MODE (XEXP (XEXP (x, 0), 0)) == mode
	  && COMPARISON_P (XEXP (XEXP (x, 0), 0))
	  && GET_MODE_PRECISION (inner_mode) <= HOST_BITS_PER_WIDE_INT
	  && (STORE_FLAG_VALUE & ~GET_MODE_MASK (inner_mode)) == 0)
	return XEXP (XEXP (x, 0), 0);

      /* Likewise for (zero_extend:DI (subreg:SI foo:DI 0)).  */
      if (GET_CODE (XEXP (x, 0)) == SUBREG
	  && GET_MODE (SUBREG_REG (XEXP (x, 0))) == mode
	  && subreg_lowpart_p (XEXP (x, 0))
	  && COMPARISON_P (SUBREG_REG (XEXP (x, 0)))
	  && GET_MODE_PRECISION (inner_mode) <= HOST_BITS_PER_WIDE_INT
	  && (STORE_FLAG_VALUE & ~GET_MODE_MASK (inner_mode)) == 0)
	return SUBREG_REG (XEXP (x, 0));

    }

  /* If we reach here, we want to return a pair of shifts.  The inner
     shift is a left shift of BITSIZE - POS - LEN bits.  The outer
     shift is a right shift of BITSIZE - LEN bits.  It is arithmetic or
     logical depending on the value of UNSIGNEDP.

     If this was a ZERO_EXTEND or ZERO_EXTRACT, this pair of shifts will be
     converted into an AND of a shift.

     We must check for the case where the left shift would have a negative
     count.  This can happen in a case like (x >> 31) & 255 on machines
     that can't shift by a constant.  On those machines, we would first
     combine the shift with the AND to produce a variable-position
     extraction.  Then the constant of 31 would be substituted in
     to produce such a position.  */

  modewidth = GET_MODE_PRECISION (mode);
  if (modewidth >= pos + len)
    {
      tem = gen_lowpart (mode, XEXP (x, 0));
      if (!tem || GET_CODE (tem) == CLOBBER)
	return x;
      tem = simplify_shift_const (NULL_RTX, ASHIFT, mode,
				  tem, modewidth - pos - len);
      tem = simplify_shift_const (NULL_RTX, unsignedp ? LSHIFTRT : ASHIFTRT,
				  mode, tem, modewidth - len);
    }
  else if (unsignedp && len < HOST_BITS_PER_WIDE_INT)
    tem = simplify_and_const_int (NULL_RTX, mode,
				  simplify_shift_const (NULL_RTX, LSHIFTRT,
							mode, XEXP (x, 0),
							pos),
				  (HOST_WIDE_INT_1U << len) - 1);
  else
    /* Any other cases we can't handle.  */
    return x;

  /* If we couldn't do this for some reason, return the original
     expression.  */
  if (GET_CODE (tem) == CLOBBER)
    return x;

  return tem;
}

/* X is a SET which contains an assignment of one object into
   a part of another (such as a bit-field assignment, STRICT_LOW_PART,
   or certain SUBREGS). If possible, convert it into a series of
   logical operations.

   We half-heartedly support variable positions, but do not at all
   support variable lengths.  */

static const_rtx
expand_field_assignment (const_rtx x)
{
  rtx inner;
  rtx pos;			/* Always counts from low bit.  */
  int len, inner_len;
  rtx mask, cleared, masked;
  scalar_int_mode compute_mode;

  /* Loop until we find something we can't simplify.  */
  while (1)
    {
      if (GET_CODE (SET_DEST (x)) == STRICT_LOW_PART
	  && GET_CODE (XEXP (SET_DEST (x), 0)) == SUBREG)
	{
	  rtx x0 = XEXP (SET_DEST (x), 0);
	  if (!GET_MODE_PRECISION (GET_MODE (x0)).is_constant (&len))
	    break;
	  inner = SUBREG_REG (XEXP (SET_DEST (x), 0));
	  pos = gen_int_mode (subreg_lsb (XEXP (SET_DEST (x), 0)),
			      MAX_MODE_INT);
	}
      else if (GET_CODE (SET_DEST (x)) == ZERO_EXTRACT
	       && CONST_INT_P (XEXP (SET_DEST (x), 1)))
	{
	  inner = XEXP (SET_DEST (x), 0);
	  if (!GET_MODE_PRECISION (GET_MODE (inner)).is_constant (&inner_len))
	    break;

	  len = INTVAL (XEXP (SET_DEST (x), 1));
	  pos = XEXP (SET_DEST (x), 2);

	  /* A constant position should stay within the width of INNER.  */
	  if (CONST_INT_P (pos) && INTVAL (pos) + len > inner_len)
	    break;

	  if (BITS_BIG_ENDIAN)
	    {
	      if (CONST_INT_P (pos))
		pos = GEN_INT (inner_len - len - INTVAL (pos));
	      else if (GET_CODE (pos) == MINUS
		       && CONST_INT_P (XEXP (pos, 1))
		       && INTVAL (XEXP (pos, 1)) == inner_len - len)
		/* If position is ADJUST - X, new position is X.  */
		pos = XEXP (pos, 0);
	      else
		pos = simplify_gen_binary (MINUS, GET_MODE (pos),
					   gen_int_mode (inner_len - len,
							 GET_MODE (pos)),
					   pos);
	    }
	}

      /* If the destination is a subreg that overwrites the whole of the inner
	 register, we can move the subreg to the source.  */
      else if (GET_CODE (SET_DEST (x)) == SUBREG
	       /* We need SUBREGs to compute nonzero_bits properly.  */
	       && nonzero_sign_valid
	       && !read_modify_subreg_p (SET_DEST (x)))
	{
	  x = gen_rtx_SET (SUBREG_REG (SET_DEST (x)),
			   gen_lowpart
			   (GET_MODE (SUBREG_REG (SET_DEST (x))),
			    SET_SRC (x)));
	  continue;
	}
      else
	break;

      while (GET_CODE (inner) == SUBREG && subreg_lowpart_p (inner))
	inner = SUBREG_REG (inner);

      /* Don't attempt bitwise arithmetic on non scalar integer modes.  */
      if (!is_a <scalar_int_mode> (GET_MODE (inner), &compute_mode))
	{
	  /* Don't do anything for vector or complex integral types.  */
	  if (! FLOAT_MODE_P (GET_MODE (inner)))
	    break;

	  /* Try to find an integral mode to pun with.  */
	  if (!int_mode_for_size (GET_MODE_BITSIZE (GET_MODE (inner)), 0)
	      .exists (&compute_mode))
	    break;

	  inner = gen_lowpart (compute_mode, inner);
	}

      /* Compute a mask of LEN bits, if we can do this on the host machine.  */
      if (len >= HOST_BITS_PER_WIDE_INT)
	break;

      /* Don't try to compute in too wide unsupported modes.  */
      if (!targetm.scalar_mode_supported_p (compute_mode))
	break;

      /* Now compute the equivalent expression.  Make a copy of INNER
	 for the SET_DEST in case it is a MEM into which we will substitute;
	 we don't want shared RTL in that case.  */
      mask = gen_int_mode ((HOST_WIDE_INT_1U << len) - 1,
			   compute_mode);
      cleared = simplify_gen_binary (AND, compute_mode,
				     simplify_gen_unary (NOT, compute_mode,
				       simplify_gen_binary (ASHIFT,
							    compute_mode,
							    mask, pos),
				       compute_mode),
				     inner);
      masked = simplify_gen_binary (ASHIFT, compute_mode,
				    simplify_gen_binary (
				      AND, compute_mode,
				      gen_lowpart (compute_mode, SET_SRC (x)),
				      mask),
				    pos);

      x = gen_rtx_SET (copy_rtx (inner),
		       simplify_gen_binary (IOR, compute_mode,
					    cleared, masked));
    }

  return x;
}

/* Return an RTX for a reference to LEN bits of INNER.  If POS_RTX is nonzero,
   it is an RTX that represents the (variable) starting position; otherwise,
   POS is the (constant) starting bit position.  Both are counted from the LSB.

   UNSIGNEDP is nonzero for an unsigned reference and zero for a signed one.

   IN_DEST is nonzero if this is a reference in the destination of a SET.
   This is used when a ZERO_ or SIGN_EXTRACT isn't needed.  If nonzero,
   a STRICT_LOW_PART will be used, if zero, ZERO_EXTEND or SIGN_EXTEND will
   be used.

   IN_COMPARE is nonzero if we are in a COMPARE.  This means that a
   ZERO_EXTRACT should be built even for bits starting at bit 0.

   MODE is the desired mode of the result (if IN_DEST == 0).

   The result is an RTX for the extraction or NULL_RTX if the target
   can't handle it.  */

static rtx
make_extraction (machine_mode mode, rtx inner, HOST_WIDE_INT pos,
		 rtx pos_rtx, unsigned HOST_WIDE_INT len, int unsignedp,
		 int in_dest, int in_compare)
{
  /* This mode describes the size of the storage area
     to fetch the overall value from.  Within that, we
     ignore the POS lowest bits, etc.  */
  machine_mode is_mode = GET_MODE (inner);
  machine_mode inner_mode;
  scalar_int_mode wanted_inner_mode;
  scalar_int_mode wanted_inner_reg_mode = word_mode;
  scalar_int_mode pos_mode = word_mode;
  machine_mode extraction_mode = word_mode;
  rtx new_rtx = 0;
  rtx orig_pos_rtx = pos_rtx;
  HOST_WIDE_INT orig_pos;

  if (pos_rtx && CONST_INT_P (pos_rtx))
    pos = INTVAL (pos_rtx), pos_rtx = 0;

  if (GET_CODE (inner) == SUBREG
      && subreg_lowpart_p (inner)
      && (paradoxical_subreg_p (inner)
	  /* If trying or potentionally trying to extract
	     bits outside of is_mode, don't look through
	     non-paradoxical SUBREGs.  See PR82192.  */
	  || (pos_rtx == NULL_RTX
	      && known_le (pos + len, GET_MODE_PRECISION (is_mode)))))
    {
      /* If going from (subreg:SI (mem:QI ...)) to (mem:QI ...),
	 consider just the QI as the memory to extract from.
	 The subreg adds or removes high bits; its mode is
	 irrelevant to the meaning of this extraction,
	 since POS and LEN count from the lsb.  */
      if (MEM_P (SUBREG_REG (inner)))
	is_mode = GET_MODE (SUBREG_REG (inner));
      inner = SUBREG_REG (inner);
    }
  else if (GET_CODE (inner) == ASHIFT
	   && CONST_INT_P (XEXP (inner, 1))
	   && pos_rtx == 0 && pos == 0
	   && len > UINTVAL (XEXP (inner, 1)))
    {
      /* We're extracting the least significant bits of an rtx
	 (ashift X (const_int C)), where LEN > C.  Extract the
	 least significant (LEN - C) bits of X, giving an rtx
	 whose mode is MODE, then shift it left C times.  */
      new_rtx = make_extraction (mode, XEXP (inner, 0),
			     0, 0, len - INTVAL (XEXP (inner, 1)),
			     unsignedp, in_dest, in_compare);
      if (new_rtx != 0)
	return gen_rtx_ASHIFT (mode, new_rtx, XEXP (inner, 1));
    }
  else if (GET_CODE (inner) == TRUNCATE
	   /* If trying or potentionally trying to extract
	      bits outside of is_mode, don't look through
	      TRUNCATE.  See PR82192.  */
	   && pos_rtx == NULL_RTX
	   && known_le (pos + len, GET_MODE_PRECISION (is_mode)))
    inner = XEXP (inner, 0);

  inner_mode = GET_MODE (inner);

  /* See if this can be done without an extraction.  We never can if the
     width of the field is not the same as that of some integer mode. For
     registers, we can only avoid the extraction if the position is at the
     low-order bit and this is either not in the destination or we have the
     appropriate STRICT_LOW_PART operation available.

     For MEM, we can avoid an extract if the field starts on an appropriate
     boundary and we can change the mode of the memory reference.  */

  scalar_int_mode tmode;
  if (int_mode_for_size (len, 1).exists (&tmode)
      && ((pos_rtx == 0 && (pos % BITS_PER_WORD) == 0
	   && !MEM_P (inner)
	   && (pos == 0 || REG_P (inner))
	   && (inner_mode == tmode
	       || !REG_P (inner)
	       || TRULY_NOOP_TRUNCATION_MODES_P (tmode, inner_mode)
	       || reg_truncated_to_mode (tmode, inner))
	   && (! in_dest
	       || (REG_P (inner)
		   && have_insn_for (STRICT_LOW_PART, tmode))))
	  || (MEM_P (inner) && pos_rtx == 0
	      && (pos
		  % (STRICT_ALIGNMENT ? GET_MODE_ALIGNMENT (tmode)
		     : BITS_PER_UNIT)) == 0
	      /* We can't do this if we are widening INNER_MODE (it
		 may not be aligned, for one thing).  */
	      && !paradoxical_subreg_p (tmode, inner_mode)
	      && (inner_mode == tmode
		  || (! mode_dependent_address_p (XEXP (inner, 0),
						  MEM_ADDR_SPACE (inner))
		      && ! MEM_VOLATILE_P (inner))))))
    {
      /* If INNER is a MEM, make a new MEM that encompasses just the desired
	 field.  If the original and current mode are the same, we need not
	 adjust the offset.  Otherwise, we do if bytes big endian.

	 If INNER is not a MEM, get a piece consisting of just the field
	 of interest (in this case POS % BITS_PER_WORD must be 0).  */

      if (MEM_P (inner))
	{
	  poly_int64 offset;

	  /* POS counts from lsb, but make OFFSET count in memory order.  */
	  if (BYTES_BIG_ENDIAN)
	    offset = bits_to_bytes_round_down (GET_MODE_PRECISION (is_mode)
					       - len - pos);
	  else
	    offset = pos / BITS_PER_UNIT;

	  new_rtx = adjust_address_nv (inner, tmode, offset);
	}
      else if (REG_P (inner))
	{
	  if (tmode != inner_mode)
	    {
	      /* We can't call gen_lowpart in a DEST since we
		 always want a SUBREG (see below) and it would sometimes
		 return a new hard register.  */
	      if (pos || in_dest)
		{
		  poly_uint64 offset
		    = subreg_offset_from_lsb (tmode, inner_mode, pos);

		  /* Avoid creating invalid subregs, for example when
		     simplifying (x>>32)&255.  */
		  if (!validate_subreg (tmode, inner_mode, inner, offset))
		    return NULL_RTX;

		  new_rtx = gen_rtx_SUBREG (tmode, inner, offset);
		}
	      else
		new_rtx = gen_lowpart (tmode, inner);
	    }
	  else
	    new_rtx = inner;
	}
      else
	new_rtx = force_to_mode (inner, tmode,
				 len >= HOST_BITS_PER_WIDE_INT
				 ? HOST_WIDE_INT_M1U
				 : (HOST_WIDE_INT_1U << len) - 1, 0);

      /* If this extraction is going into the destination of a SET,
	 make a STRICT_LOW_PART unless we made a MEM.  */

      if (in_dest)
	return (MEM_P (new_rtx) ? new_rtx
		: (GET_CODE (new_rtx) != SUBREG
		   ? gen_rtx_CLOBBER (tmode, const0_rtx)
		   : gen_rtx_STRICT_LOW_PART (VOIDmode, new_rtx)));

      if (mode == tmode)
	return new_rtx;

      if (CONST_SCALAR_INT_P (new_rtx))
	return simplify_unary_operation (unsignedp ? ZERO_EXTEND : SIGN_EXTEND,
					 mode, new_rtx, tmode);

      /* If we know that no extraneous bits are set, and that the high
	 bit is not set, convert the extraction to the cheaper of
	 sign and zero extension, that are equivalent in these cases.  */
      if (flag_expensive_optimizations
	  && (HWI_COMPUTABLE_MODE_P (tmode)
	      && ((nonzero_bits (new_rtx, tmode)
		   & ~(((unsigned HOST_WIDE_INT)GET_MODE_MASK (tmode)) >> 1))
		  == 0)))
	{
	  rtx temp = gen_rtx_ZERO_EXTEND (mode, new_rtx);
	  rtx temp1 = gen_rtx_SIGN_EXTEND (mode, new_rtx);

	  /* Prefer ZERO_EXTENSION, since it gives more information to
	     backends.  */
	  if (set_src_cost (temp, mode, optimize_this_for_speed_p)
	      <= set_src_cost (temp1, mode, optimize_this_for_speed_p))
	    return temp;
	  return temp1;
	}

      /* Otherwise, sign- or zero-extend unless we already are in the
	 proper mode.  */

      return (gen_rtx_fmt_e (unsignedp ? ZERO_EXTEND : SIGN_EXTEND,
			     mode, new_rtx));
    }

  /* Unless this is a COMPARE or we have a funny memory reference,
     don't do anything with zero-extending field extracts starting at
     the low-order bit since they are simple AND operations.  */
  if (pos_rtx == 0 && pos == 0 && ! in_dest
      && ! in_compare && unsignedp)
    return 0;

  /* Unless INNER is not MEM, reject this if we would be spanning bytes or
     if the position is not a constant and the length is not 1.  In all
     other cases, we would only be going outside our object in cases when
     an original shift would have been undefined.  */
  if (MEM_P (inner)
      && ((pos_rtx == 0 && maybe_gt (pos + len, GET_MODE_PRECISION (is_mode)))
	  || (pos_rtx != 0 && len != 1)))
    return 0;

  enum extraction_pattern pattern = (in_dest ? EP_insv
				     : unsignedp ? EP_extzv : EP_extv);

  /* If INNER is not from memory, we want it to have the mode of a register
     extraction pattern's structure operand, or word_mode if there is no
     such pattern.  The same applies to extraction_mode and pos_mode
     and their respective operands.

     For memory, assume that the desired extraction_mode and pos_mode
     are the same as for a register operation, since at present we don't
     have named patterns for aligned memory structures.  */
  struct extraction_insn insn;
  unsigned int inner_size;
  if (GET_MODE_BITSIZE (inner_mode).is_constant (&inner_size)
      && get_best_reg_extraction_insn (&insn, pattern, inner_size, mode))
    {
      wanted_inner_reg_mode = insn.struct_mode.require ();
      pos_mode = insn.pos_mode;
      extraction_mode = insn.field_mode;
    }

  /* Never narrow an object, since that might not be safe.  */

  if (mode != VOIDmode
      && partial_subreg_p (extraction_mode, mode))
    extraction_mode = mode;

  if (!MEM_P (inner))
    wanted_inner_mode = wanted_inner_reg_mode;
  else
    {
      /* Be careful not to go beyond the extracted object and maintain the
	 natural alignment of the memory.  */
      wanted_inner_mode = smallest_int_mode_for_size (len);
      while (pos % GET_MODE_BITSIZE (wanted_inner_mode) + len
	     > GET_MODE_BITSIZE (wanted_inner_mode))
	wanted_inner_mode = GET_MODE_WIDER_MODE (wanted_inner_mode).require ();
    }

  orig_pos = pos;

  if (BITS_BIG_ENDIAN)
    {
      /* POS is passed as if BITS_BIG_ENDIAN == 0, so we need to convert it to
	 BITS_BIG_ENDIAN style.  If position is constant, compute new
	 position.  Otherwise, build subtraction.
	 Note that POS is relative to the mode of the original argument.
	 If it's a MEM we need to recompute POS relative to that.
	 However, if we're extracting from (or inserting into) a register,
	 we want to recompute POS relative to wanted_inner_mode.  */
      int width;
      if (!MEM_P (inner))
	width = GET_MODE_BITSIZE (wanted_inner_mode);
      else if (!GET_MODE_BITSIZE (is_mode).is_constant (&width))
	return NULL_RTX;

      if (pos_rtx == 0)
	pos = width - len - pos;
      else
	pos_rtx
	  = gen_rtx_MINUS (GET_MODE (pos_rtx),
			   gen_int_mode (width - len, GET_MODE (pos_rtx)),
			   pos_rtx);
      /* POS may be less than 0 now, but we check for that below.
	 Note that it can only be less than 0 if !MEM_P (inner).  */
    }

  /* If INNER has a wider mode, and this is a constant extraction, try to
     make it smaller and adjust the byte to point to the byte containing
     the value.  */
  if (wanted_inner_mode != VOIDmode
      && inner_mode != wanted_inner_mode
      && ! pos_rtx
      && partial_subreg_p (wanted_inner_mode, is_mode)
      && MEM_P (inner)
      && ! mode_dependent_address_p (XEXP (inner, 0), MEM_ADDR_SPACE (inner))
      && ! MEM_VOLATILE_P (inner))
    {
      poly_int64 offset = 0;

      /* The computations below will be correct if the machine is big
	 endian in both bits and bytes or little endian in bits and bytes.
	 If it is mixed, we must adjust.  */

      /* If bytes are big endian and we had a paradoxical SUBREG, we must
	 adjust OFFSET to compensate.  */
      if (BYTES_BIG_ENDIAN
	  && paradoxical_subreg_p (is_mode, inner_mode))
	offset -= GET_MODE_SIZE (is_mode) - GET_MODE_SIZE (inner_mode);

      /* We can now move to the desired byte.  */
      offset += (pos / GET_MODE_BITSIZE (wanted_inner_mode))
		* GET_MODE_SIZE (wanted_inner_mode);
      pos %= GET_MODE_BITSIZE (wanted_inner_mode);

      if (BYTES_BIG_ENDIAN != BITS_BIG_ENDIAN
	  && is_mode != wanted_inner_mode)
	offset = (GET_MODE_SIZE (is_mode)
		  - GET_MODE_SIZE (wanted_inner_mode) - offset);

      inner = adjust_address_nv (inner, wanted_inner_mode, offset);
    }

  /* If INNER is not memory, get it into the proper mode.  If we are changing
     its mode, POS must be a constant and smaller than the size of the new
     mode.  */
  else if (!MEM_P (inner))
    {
      /* On the LHS, don't create paradoxical subregs implicitely truncating
	 the register unless TARGET_TRULY_NOOP_TRUNCATION.  */
      if (in_dest
	  && !TRULY_NOOP_TRUNCATION_MODES_P (GET_MODE (inner),
					     wanted_inner_mode))
	return NULL_RTX;

      if (GET_MODE (inner) != wanted_inner_mode
	  && (pos_rtx != 0
	      || orig_pos + len > GET_MODE_BITSIZE (wanted_inner_mode)))
	return NULL_RTX;

      if (orig_pos < 0)
	return NULL_RTX;

      inner = force_to_mode (inner, wanted_inner_mode,
			     pos_rtx
			     || len + orig_pos >= HOST_BITS_PER_WIDE_INT
			     ? HOST_WIDE_INT_M1U
			     : (((HOST_WIDE_INT_1U << len) - 1)
				<< orig_pos),
			     0);
    }

  /* Adjust mode of POS_RTX, if needed.  If we want a wider mode, we
     have to zero extend.  Otherwise, we can just use a SUBREG.

     We dealt with constant rtxes earlier, so pos_rtx cannot
     have VOIDmode at this point.  */
  if (pos_rtx != 0
      && (GET_MODE_SIZE (pos_mode)
	  > GET_MODE_SIZE (as_a <scalar_int_mode> (GET_MODE (pos_rtx)))))
    {
      rtx temp = simplify_gen_unary (ZERO_EXTEND, pos_mode, pos_rtx,
				     GET_MODE (pos_rtx));

      /* If we know that no extraneous bits are set, and that the high
	 bit is not set, convert extraction to cheaper one - either
	 SIGN_EXTENSION or ZERO_EXTENSION, that are equivalent in these
	 cases.  */
      if (flag_expensive_optimizations
	  && (HWI_COMPUTABLE_MODE_P (GET_MODE (pos_rtx))
	      && ((nonzero_bits (pos_rtx, GET_MODE (pos_rtx))
		   & ~(((unsigned HOST_WIDE_INT)
			GET_MODE_MASK (GET_MODE (pos_rtx)))
		       >> 1))
		  == 0)))
	{
	  rtx temp1 = simplify_gen_unary (SIGN_EXTEND, pos_mode, pos_rtx,
					  GET_MODE (pos_rtx));

	  /* Prefer ZERO_EXTENSION, since it gives more information to
	     backends.  */
	  if (set_src_cost (temp1, pos_mode, optimize_this_for_speed_p)
	      < set_src_cost (temp, pos_mode, optimize_this_for_speed_p))
	    temp = temp1;
	}
      pos_rtx = temp;
    }

  /* Make POS_RTX unless we already have it and it is correct.  If we don't
     have a POS_RTX but we do have an ORIG_POS_RTX, the latter must
     be a CONST_INT.  */
  if (pos_rtx == 0 && orig_pos_rtx != 0 && INTVAL (orig_pos_rtx) == pos)
    pos_rtx = orig_pos_rtx;

  else if (pos_rtx == 0)
    pos_rtx = GEN_INT (pos);

  /* Make the required operation.  See if we can use existing rtx.  */
  new_rtx = gen_rtx_fmt_eee (unsignedp ? ZERO_EXTRACT : SIGN_EXTRACT,
			 extraction_mode, inner, GEN_INT (len), pos_rtx);
  if (! in_dest)
    new_rtx = gen_lowpart (mode, new_rtx);

  return new_rtx;
}

/* See if X (of mode MODE) contains an ASHIFT of COUNT or more bits that
   can be commuted with any other operations in X.  Return X without
   that shift if so.  */

static rtx
extract_left_shift (scalar_int_mode mode, rtx x, int count)
{
  enum rtx_code code = GET_CODE (x);
  rtx tem;

  switch (code)
    {
    case ASHIFT:
      /* This is the shift itself.  If it is wide enough, we will return
	 either the value being shifted if the shift count is equal to
	 COUNT or a shift for the difference.  */
      if (CONST_INT_P (XEXP (x, 1))
	  && INTVAL (XEXP (x, 1)) >= count)
	return simplify_shift_const (NULL_RTX, ASHIFT, mode, XEXP (x, 0),
				     INTVAL (XEXP (x, 1)) - count);
      break;

    case NEG:  case NOT:
      if ((tem = extract_left_shift (mode, XEXP (x, 0), count)) != 0)
	return simplify_gen_unary (code, mode, tem, mode);

      break;

    case PLUS:  case IOR:  case XOR:  case AND:
      /* If we can safely shift this constant and we find the inner shift,
	 make a new operation.  */
      if (CONST_INT_P (XEXP (x, 1))
	  && (UINTVAL (XEXP (x, 1))
	      & (((HOST_WIDE_INT_1U << count)) - 1)) == 0
	  && (tem = extract_left_shift (mode, XEXP (x, 0), count)) != 0)
	{
	  HOST_WIDE_INT val = INTVAL (XEXP (x, 1)) >> count;
	  return simplify_gen_binary (code, mode, tem,
				      gen_int_mode (val, mode));
	}
      break;

    default:
      break;
    }

  return 0;
}

/* Subroutine of make_compound_operation.  *X_PTR is the rtx at the current
   level of the expression and MODE is its mode.  IN_CODE is as for
   make_compound_operation.  *NEXT_CODE_PTR is the value of IN_CODE
   that should be used when recursing on operands of *X_PTR.

   There are two possible actions:

   - Return null.  This tells the caller to recurse on *X_PTR with IN_CODE
     equal to *NEXT_CODE_PTR, after which *X_PTR holds the final value.

   - Return a new rtx, which the caller returns directly.  */

static rtx
make_compound_operation_int (scalar_int_mode mode, rtx *x_ptr,
			     enum rtx_code in_code,
			     enum rtx_code *next_code_ptr)
{
  rtx x = *x_ptr;
  enum rtx_code next_code = *next_code_ptr;
  enum rtx_code code = GET_CODE (x);
  int mode_width = GET_MODE_PRECISION (mode);
  rtx rhs, lhs;
  rtx new_rtx = 0;
  int i;
  rtx tem;
  scalar_int_mode inner_mode;
  bool equality_comparison = false;

  if (in_code == EQ)
    {
      equality_comparison = true;
      in_code = COMPARE;
    }

  /* Process depending on the code of this operation.  If NEW is set
     nonzero, it will be returned.  */

  switch (code)
    {
    case ASHIFT:
      /* Convert shifts by constants into multiplications if inside
	 an address.  */
      if (in_code == MEM && CONST_INT_P (XEXP (x, 1))
	  && INTVAL (XEXP (x, 1)) < HOST_BITS_PER_WIDE_INT
	  && INTVAL (XEXP (x, 1)) >= 0)
	{
	  HOST_WIDE_INT count = INTVAL (XEXP (x, 1));
	  HOST_WIDE_INT multval = HOST_WIDE_INT_1 << count;

	  new_rtx = make_compound_operation (XEXP (x, 0), next_code);
	  if (GET_CODE (new_rtx) == NEG)
	    {
	      new_rtx = XEXP (new_rtx, 0);
	      multval = -multval;
	    }
	  multval = trunc_int_for_mode (multval, mode);
	  new_rtx = gen_rtx_MULT (mode, new_rtx, gen_int_mode (multval, mode));
	}
      break;

    case PLUS:
      lhs = XEXP (x, 0);
      rhs = XEXP (x, 1);
      lhs = make_compound_operation (lhs, next_code);
      rhs = make_compound_operation (rhs, next_code);
      if (GET_CODE (lhs) == MULT && GET_CODE (XEXP (lhs, 0)) == NEG)
	{
	  tem = simplify_gen_binary (MULT, mode, XEXP (XEXP (lhs, 0), 0),
				     XEXP (lhs, 1));
	  new_rtx = simplify_gen_binary (MINUS, mode, rhs, tem);
	}
      else if (GET_CODE (lhs) == MULT
	       && (CONST_INT_P (XEXP (lhs, 1)) && INTVAL (XEXP (lhs, 1)) < 0))
	{
	  tem = simplify_gen_binary (MULT, mode, XEXP (lhs, 0),
				     simplify_gen_unary (NEG, mode,
							 XEXP (lhs, 1),
							 mode));
	  new_rtx = simplify_gen_binary (MINUS, mode, rhs, tem);
	}
      else
	{
	  SUBST (XEXP (x, 0), lhs);
	  SUBST (XEXP (x, 1), rhs);
	}
      maybe_swap_commutative_operands (x);
      return x;

    case MINUS:
      lhs = XEXP (x, 0);
      rhs = XEXP (x, 1);
      lhs = make_compound_operation (lhs, next_code);
      rhs = make_compound_operation (rhs, next_code);
      if (GET_CODE (rhs) == MULT && GET_CODE (XEXP (rhs, 0)) == NEG)
	{
	  tem = simplify_gen_binary (MULT, mode, XEXP (XEXP (rhs, 0), 0),
				     XEXP (rhs, 1));
	  return simplify_gen_binary (PLUS, mode, tem, lhs);
	}
      else if (GET_CODE (rhs) == MULT
	       && (CONST_INT_P (XEXP (rhs, 1)) && INTVAL (XEXP (rhs, 1)) < 0))
	{
	  tem = simplify_gen_binary (MULT, mode, XEXP (rhs, 0),
				     simplify_gen_unary (NEG, mode,
							 XEXP (rhs, 1),
							 mode));
	  return simplify_gen_binary (PLUS, mode, tem, lhs);
	}
      else
	{
	  SUBST (XEXP (x, 0), lhs);
	  SUBST (XEXP (x, 1), rhs);
	  return x;
	}

    case AND:
      /* If the second operand is not a constant, we can't do anything
	 with it.  */
      if (!CONST_INT_P (XEXP (x, 1)))
	break;

      /* If the constant is a power of two minus one and the first operand
	 is a logical right shift, make an extraction.  */
      if (GET_CODE (XEXP (x, 0)) == LSHIFTRT
	  && (i = exact_log2 (UINTVAL (XEXP (x, 1)) + 1)) >= 0)
	{
	  new_rtx = make_compound_operation (XEXP (XEXP (x, 0), 0), next_code);
	  new_rtx = make_extraction (mode, new_rtx, 0, XEXP (XEXP (x, 0), 1),
				     i, 1, 0, in_code == COMPARE);
	}

      /* Same as previous, but for (subreg (lshiftrt ...)) in first op.  */
      else if (GET_CODE (XEXP (x, 0)) == SUBREG
	       && subreg_lowpart_p (XEXP (x, 0))
	       && is_a <scalar_int_mode> (GET_MODE (SUBREG_REG (XEXP (x, 0))),
					  &inner_mode)
	       && GET_CODE (SUBREG_REG (XEXP (x, 0))) == LSHIFTRT
	       && (i = exact_log2 (UINTVAL (XEXP (x, 1)) + 1)) >= 0)
	{
	  rtx inner_x0 = SUBREG_REG (XEXP (x, 0));
	  new_rtx = make_compound_operation (XEXP (inner_x0, 0), next_code);
	  new_rtx = make_extraction (inner_mode, new_rtx, 0,
				     XEXP (inner_x0, 1),
				     i, 1, 0, in_code == COMPARE);

	  /* If we narrowed the mode when dropping the subreg, then we lose.  */
	  if (GET_MODE_SIZE (inner_mode) < GET_MODE_SIZE (mode))
	    new_rtx = NULL;

	  /* If that didn't give anything, see if the AND simplifies on
	     its own.  */
	  if (!new_rtx && i >= 0)
	    {
	      new_rtx = make_compound_operation (XEXP (x, 0), next_code);
	      new_rtx = make_extraction (mode, new_rtx, 0, NULL_RTX, i, 1,
					 0, in_code == COMPARE);
	    }
	}
      /* Same as previous, but for (xor/ior (lshiftrt...) (lshiftrt...)).  */
      else if ((GET_CODE (XEXP (x, 0)) == XOR
		|| GET_CODE (XEXP (x, 0)) == IOR)
	       && GET_CODE (XEXP (XEXP (x, 0), 0)) == LSHIFTRT
	       && GET_CODE (XEXP (XEXP (x, 0), 1)) == LSHIFTRT
	       && (i = exact_log2 (UINTVAL (XEXP (x, 1)) + 1)) >= 0)
	{
	  /* Apply the distributive law, and then try to make extractions.  */
	  new_rtx = gen_rtx_fmt_ee (GET_CODE (XEXP (x, 0)), mode,
				    gen_rtx_AND (mode, XEXP (XEXP (x, 0), 0),
						 XEXP (x, 1)),
				    gen_rtx_AND (mode, XEXP (XEXP (x, 0), 1),
						 XEXP (x, 1)));
	  new_rtx = make_compound_operation (new_rtx, in_code);
	}

      /* If we are have (and (rotate X C) M) and C is larger than the number
	 of bits in M, this is an extraction.  */

      else if (GET_CODE (XEXP (x, 0)) == ROTATE
	       && CONST_INT_P (XEXP (XEXP (x, 0), 1))
	       && (i = exact_log2 (UINTVAL (XEXP (x, 1)) + 1)) >= 0
	       && i <= INTVAL (XEXP (XEXP (x, 0), 1)))
	{
	  new_rtx = make_compound_operation (XEXP (XEXP (x, 0), 0), next_code);
	  new_rtx = make_extraction (mode, new_rtx,
				     (GET_MODE_PRECISION (mode)
				      - INTVAL (XEXP (XEXP (x, 0), 1))),
				     NULL_RTX, i, 1, 0, in_code == COMPARE);
	}

      /* On machines without logical shifts, if the operand of the AND is
	 a logical shift and our mask turns off all the propagated sign
	 bits, we can replace the logical shift with an arithmetic shift.  */
      else if (GET_CODE (XEXP (x, 0)) == LSHIFTRT
	       && !have_insn_for (LSHIFTRT, mode)
	       && have_insn_for (ASHIFTRT, mode)
	       && CONST_INT_P (XEXP (XEXP (x, 0), 1))
	       && INTVAL (XEXP (XEXP (x, 0), 1)) >= 0
	       && INTVAL (XEXP (XEXP (x, 0), 1)) < HOST_BITS_PER_WIDE_INT
	       && mode_width <= HOST_BITS_PER_WIDE_INT)
	{
	  unsigned HOST_WIDE_INT mask = GET_MODE_MASK (mode);

	  mask >>= INTVAL (XEXP (XEXP (x, 0), 1));
	  if ((INTVAL (XEXP (x, 1)) & ~mask) == 0)
	    SUBST (XEXP (x, 0),
		   gen_rtx_ASHIFTRT (mode,
				     make_compound_operation (XEXP (XEXP (x,
									  0),
								    0),
							      next_code),
				     XEXP (XEXP (x, 0), 1)));
	}

      /* If the constant is one less than a power of two, this might be
	 representable by an extraction even if no shift is present.
	 If it doesn't end up being a ZERO_EXTEND, we will ignore it unless
	 we are in a COMPARE.  */
      else if ((i = exact_log2 (UINTVAL (XEXP (x, 1)) + 1)) >= 0)
	new_rtx = make_extraction (mode,
				   make_compound_operation (XEXP (x, 0),
							    next_code),
				   0, NULL_RTX, i, 1, 0, in_code == COMPARE);

      /* If we are in a comparison and this is an AND with a power of two,
	 convert this into the appropriate bit extract.  */
      else if (in_code == COMPARE
	       && (i = exact_log2 (UINTVAL (XEXP (x, 1)))) >= 0
	       && (equality_comparison || i < GET_MODE_PRECISION (mode) - 1))
	new_rtx = make_extraction (mode,
				   make_compound_operation (XEXP (x, 0),
							    next_code),
				   i, NULL_RTX, 1, 1, 0, 1);

      /* If the one operand is a paradoxical subreg of a register or memory and
	 the constant (limited to the smaller mode) has only zero bits where
	 the sub expression has known zero bits, this can be expressed as
	 a zero_extend.  */
      else if (GET_CODE (XEXP (x, 0)) == SUBREG)
	{
	  rtx sub;

	  sub = XEXP (XEXP (x, 0), 0);
	  machine_mode sub_mode = GET_MODE (sub);
	  int sub_width;
	  if ((REG_P (sub) || MEM_P (sub))
	      && GET_MODE_PRECISION (sub_mode).is_constant (&sub_width)
	      && sub_width < mode_width)
	    {
	      unsigned HOST_WIDE_INT mode_mask = GET_MODE_MASK (sub_mode);
	      unsigned HOST_WIDE_INT mask;

	      /* original AND constant with all the known zero bits set */
	      mask = UINTVAL (XEXP (x, 1)) | (~nonzero_bits (sub, sub_mode));
	      if ((mask & mode_mask) == mode_mask)
		{
		  new_rtx = make_compound_operation (sub, next_code);
		  new_rtx = make_extraction (mode, new_rtx, 0, 0, sub_width,
					     1, 0, in_code == COMPARE);
		}
	    }
	}

      break;

    case LSHIFTRT:
      /* If the sign bit is known to be zero, replace this with an
	 arithmetic shift.  */
      if (have_insn_for (ASHIFTRT, mode)
	  && ! have_insn_for (LSHIFTRT, mode)
	  && mode_width <= HOST_BITS_PER_WIDE_INT
	  && (nonzero_bits (XEXP (x, 0), mode) & (1 << (mode_width - 1))) == 0)
	{
	  new_rtx = gen_rtx_ASHIFTRT (mode,
				      make_compound_operation (XEXP (x, 0),
							       next_code),
				      XEXP (x, 1));
	  break;
	}

      /* fall through */

    case ASHIFTRT:
      lhs = XEXP (x, 0);
      rhs = XEXP (x, 1);

      /* If we have (ashiftrt (ashift foo C1) C2) with C2 >= C1,
	 this is a SIGN_EXTRACT.  */
      if (CONST_INT_P (rhs)
	  && GET_CODE (lhs) == ASHIFT
	  && CONST_INT_P (XEXP (lhs, 1))
	  && INTVAL (rhs) >= INTVAL (XEXP (lhs, 1))
	  && INTVAL (XEXP (lhs, 1)) >= 0
	  && INTVAL (rhs) < mode_width)
	{
	  new_rtx = make_compound_operation (XEXP (lhs, 0), next_code);
	  new_rtx = make_extraction (mode, new_rtx,
				     INTVAL (rhs) - INTVAL (XEXP (lhs, 1)),
				     NULL_RTX, mode_width - INTVAL (rhs),
				     code == LSHIFTRT, 0, in_code == COMPARE);
	  break;
	}

      /* See if we have operations between an ASHIFTRT and an ASHIFT.
	 If so, try to merge the shifts into a SIGN_EXTEND.  We could
	 also do this for some cases of SIGN_EXTRACT, but it doesn't
	 seem worth the effort; the case checked for occurs on Alpha.  */

      if (!OBJECT_P (lhs)
	  && ! (GET_CODE (lhs) == SUBREG
		&& (OBJECT_P (SUBREG_REG (lhs))))
	  && CONST_INT_P (rhs)
	  && INTVAL (rhs) >= 0
	  && INTVAL (rhs) < HOST_BITS_PER_WIDE_INT
	  && INTVAL (rhs) < mode_width
	  && (new_rtx = extract_left_shift (mode, lhs, INTVAL (rhs))) != 0)
	new_rtx = make_extraction (mode, make_compound_operation (new_rtx,
								  next_code),
				   0, NULL_RTX, mode_width - INTVAL (rhs),
				   code == LSHIFTRT, 0, in_code == COMPARE);

      break;

    case SUBREG:
      /* Call ourselves recursively on the inner expression.  If we are
	 narrowing the object and it has a different RTL code from
	 what it originally did, do this SUBREG as a force_to_mode.  */
      {
	rtx inner = SUBREG_REG (x), simplified;
	enum rtx_code subreg_code = in_code;

	/* If the SUBREG is masking of a logical right shift,
	   make an extraction.  */
	if (GET_CODE (inner) == LSHIFTRT
	    && is_a <scalar_int_mode> (GET_MODE (inner), &inner_mode)
	    && GET_MODE_SIZE (mode) < GET_MODE_SIZE (inner_mode)
	    && CONST_INT_P (XEXP (inner, 1))
	    && UINTVAL (XEXP (inner, 1)) < GET_MODE_PRECISION (inner_mode)
	    && subreg_lowpart_p (x))
	  {
	    new_rtx = make_compound_operation (XEXP (inner, 0), next_code);
	    int width = GET_MODE_PRECISION (inner_mode)
			- INTVAL (XEXP (inner, 1));
	    if (width > mode_width)
	      width = mode_width;
	    new_rtx = make_extraction (mode, new_rtx, 0, XEXP (inner, 1),
				       width, 1, 0, in_code == COMPARE);
	    break;
	  }

	/* If in_code is COMPARE, it isn't always safe to pass it through
	   to the recursive make_compound_operation call.  */
	if (subreg_code == COMPARE
	    && (!subreg_lowpart_p (x)
		|| GET_CODE (inner) == SUBREG
		/* (subreg:SI (and:DI (reg:DI) (const_int 0x800000000)) 0)
		   is (const_int 0), rather than
		   (subreg:SI (lshiftrt:DI (reg:DI) (const_int 35)) 0).
		   Similarly (subreg:QI (and:SI (reg:SI) (const_int 0x80)) 0)
		   for non-equality comparisons against 0 is not equivalent
		   to (subreg:QI (lshiftrt:SI (reg:SI) (const_int 7)) 0).  */
		|| (GET_CODE (inner) == AND
		    && CONST_INT_P (XEXP (inner, 1))
		    && partial_subreg_p (x)
		    && exact_log2 (UINTVAL (XEXP (inner, 1)))
		       >= GET_MODE_BITSIZE (mode) - 1)))
	  subreg_code = SET;

	tem = make_compound_operation (inner, subreg_code);

	simplified
	  = simplify_subreg (mode, tem, GET_MODE (inner), SUBREG_BYTE (x));
	if (simplified)
	  tem = simplified;

	if (GET_CODE (tem) != GET_CODE (inner)
	    && partial_subreg_p (x)
	    && subreg_lowpart_p (x))
	  {
	    rtx newer
	      = force_to_mode (tem, mode, HOST_WIDE_INT_M1U, 0);

	    /* If we have something other than a SUBREG, we might have
	       done an expansion, so rerun ourselves.  */
	    if (GET_CODE (newer) != SUBREG)
	      newer = make_compound_operation (newer, in_code);

	    /* force_to_mode can expand compounds.  If it just re-expanded
	       the compound, use gen_lowpart to convert to the desired
	       mode.  */
	    if (rtx_equal_p (newer, x)
		/* Likewise if it re-expanded the compound only partially.
		   This happens for SUBREG of ZERO_EXTRACT if they extract
		   the same number of bits.  */
		|| (GET_CODE (newer) == SUBREG
		    && (GET_CODE (SUBREG_REG (newer)) == LSHIFTRT
			|| GET_CODE (SUBREG_REG (newer)) == ASHIFTRT)
		    && GET_CODE (inner) == AND
		    && rtx_equal_p (SUBREG_REG (newer), XEXP (inner, 0))))
	      return gen_lowpart (GET_MODE (x), tem);

	    return newer;
	  }

	if (simplified)
	  return tem;
      }
      break;

    default:
      break;
    }

  if (new_rtx)
    *x_ptr = gen_lowpart (mode, new_rtx);
  *next_code_ptr = next_code;
  return NULL_RTX;
}

/* Look at the expression rooted at X.  Look for expressions
   equivalent to ZERO_EXTRACT, SIGN_EXTRACT, ZERO_EXTEND, SIGN_EXTEND.
   Form these expressions.

   Return the new rtx, usually just X.

   Also, for machines like the VAX that don't have logical shift insns,
   try to convert logical to arithmetic shift operations in cases where
   they are equivalent.  This undoes the canonicalizations to logical
   shifts done elsewhere.

   We try, as much as possible, to re-use rtl expressions to save memory.

   IN_CODE says what kind of expression we are processing.  Normally, it is
   SET.  In a memory address it is MEM.  When processing the arguments of
   a comparison or a COMPARE against zero, it is COMPARE, or EQ if more
   precisely it is an equality comparison against zero.  */

rtx
make_compound_operation (rtx x, enum rtx_code in_code)
{
  enum rtx_code code = GET_CODE (x);
  const char *fmt;
  int i, j;
  enum rtx_code next_code;
  rtx new_rtx, tem;

  /* Select the code to be used in recursive calls.  Once we are inside an
     address, we stay there.  If we have a comparison, set to COMPARE,
     but once inside, go back to our default of SET.  */

  next_code = (code == MEM ? MEM
	       : ((code == COMPARE || COMPARISON_P (x))
		  && XEXP (x, 1) == const0_rtx) ? COMPARE
	       : in_code == COMPARE || in_code == EQ ? SET : in_code);

  scalar_int_mode mode;
  if (is_a <scalar_int_mode> (GET_MODE (x), &mode))
    {
      rtx new_rtx = make_compound_operation_int (mode, &x, in_code,
						 &next_code);
      if (new_rtx)
	return new_rtx;
      code = GET_CODE (x);
    }

  /* Now recursively process each operand of this operation.  We need to
     handle ZERO_EXTEND specially so that we don't lose track of the
     inner mode.  */
  if (code == ZERO_EXTEND)
    {
      new_rtx = make_compound_operation (XEXP (x, 0), next_code);
      tem = simplify_const_unary_operation (ZERO_EXTEND, GET_MODE (x),
					    new_rtx, GET_MODE (XEXP (x, 0)));
      if (tem)
	return tem;
      SUBST (XEXP (x, 0), new_rtx);
      return x;
    }

  fmt = GET_RTX_FORMAT (code);
  for (i = 0; i < GET_RTX_LENGTH (code); i++)
    if (fmt[i] == 'e')
      {
	new_rtx = make_compound_operation (XEXP (x, i), next_code);
	SUBST (XEXP (x, i), new_rtx);
      }
    else if (fmt[i] == 'E')
      for (j = 0; j < XVECLEN (x, i); j++)
	{
	  new_rtx = make_compound_operation (XVECEXP (x, i, j), next_code);
	  SUBST (XVECEXP (x, i, j), new_rtx);
	}

  maybe_swap_commutative_operands (x);
  return x;
}

/* Given M see if it is a value that would select a field of bits
   within an item, but not the entire word.  Return -1 if not.
   Otherwise, return the starting position of the field, where 0 is the
   low-order bit.

   *PLEN is set to the length of the field.  */

static int
get_pos_from_mask (unsigned HOST_WIDE_INT m, unsigned HOST_WIDE_INT *plen)
{
  /* Get the bit number of the first 1 bit from the right, -1 if none.  */
  int pos = m ? ctz_hwi (m) : -1;
  int len = 0;

  if (pos >= 0)
    /* Now shift off the low-order zero bits and see if we have a
       power of two minus 1.  */
    len = exact_log2 ((m >> pos) + 1);

  if (len <= 0)
    pos = -1;

  *plen = len;
  return pos;
}

/* If X refers to a register that equals REG in value, replace these
   references with REG.  */
static rtx
canon_reg_for_combine (rtx x, rtx reg)
{
  rtx op0, op1, op2;
  const char *fmt;
  int i;
  bool copied;

  enum rtx_code code = GET_CODE (x);
  switch (GET_RTX_CLASS (code))
    {
    case RTX_UNARY:
      op0 = canon_reg_for_combine (XEXP (x, 0), reg);
      if (op0 != XEXP (x, 0))
	return simplify_gen_unary (GET_CODE (x), GET_MODE (x), op0,
				   GET_MODE (reg));
      break;

    case RTX_BIN_ARITH:
    case RTX_COMM_ARITH:
      op0 = canon_reg_for_combine (XEXP (x, 0), reg);
      op1 = canon_reg_for_combine (XEXP (x, 1), reg);
      if (op0 != XEXP (x, 0) || op1 != XEXP (x, 1))
	return simplify_gen_binary (GET_CODE (x), GET_MODE (x), op0, op1);
      break;

    case RTX_COMPARE:
    case RTX_COMM_COMPARE:
      op0 = canon_reg_for_combine (XEXP (x, 0), reg);
      op1 = canon_reg_for_combine (XEXP (x, 1), reg);
      if (op0 != XEXP (x, 0) || op1 != XEXP (x, 1))
	return simplify_gen_relational (GET_CODE (x), GET_MODE (x),
					GET_MODE (op0), op0, op1);
      break;

    case RTX_TERNARY:
    case RTX_BITFIELD_OPS:
      op0 = canon_reg_for_combine (XEXP (x, 0), reg);
      op1 = canon_reg_for_combine (XEXP (x, 1), reg);
      op2 = canon_reg_for_combine (XEXP (x, 2), reg);
      if (op0 != XEXP (x, 0) || op1 != XEXP (x, 1) || op2 != XEXP (x, 2))
	return simplify_gen_ternary (GET_CODE (x), GET_MODE (x),
				     GET_MODE (op0), op0, op1, op2);
      /* FALLTHRU */

    case RTX_OBJ:
      if (REG_P (x))
	{
	  if (rtx_equal_p (get_last_value (reg), x)
	      || rtx_equal_p (reg, get_last_value (x)))
	    return reg;
	  else
	    break;
	}

      /* fall through */

    default:
      fmt = GET_RTX_FORMAT (code);
      copied = false;
      for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
	if (fmt[i] == 'e')
	  {
	    rtx op = canon_reg_for_combine (XEXP (x, i), reg);
	    if (op != XEXP (x, i))
	      {
		if (!copied)
		  {
		    copied = true;
		    x = copy_rtx (x);
		  }
		XEXP (x, i) = op;
	      }
	  }
	else if (fmt[i] == 'E')
	  {
	    int j;
	    for (j = 0; j < XVECLEN (x, i); j++)
	      {
		rtx op = canon_reg_for_combine (XVECEXP (x, i, j), reg);
		if (op != XVECEXP (x, i, j))
		  {
		    if (!copied)
		      {
			copied = true;
			x = copy_rtx (x);
		      }
		    XVECEXP (x, i, j) = op;
		  }
	      }
	  }

      break;
    }

  return x;
}

/* Return X converted to MODE.  If the value is already truncated to
   MODE we can just return a subreg even though in the general case we
   would need an explicit truncation.  */

static rtx
gen_lowpart_or_truncate (machine_mode mode, rtx x)
{
  if (!CONST_INT_P (x)
      && partial_subreg_p (mode, GET_MODE (x))
      && !TRULY_NOOP_TRUNCATION_MODES_P (mode, GET_MODE (x))
      && !(REG_P (x) && reg_truncated_to_mode (mode, x)))
    {
      /* Bit-cast X into an integer mode.  */
      if (!SCALAR_INT_MODE_P (GET_MODE (x)))
	x = gen_lowpart (int_mode_for_mode (GET_MODE (x)).require (), x);
      x = simplify_gen_unary (TRUNCATE, int_mode_for_mode (mode).require (),
			      x, GET_MODE (x));
    }

  return gen_lowpart (mode, x);
}

/* See if X can be simplified knowing that we will only refer to it in
   MODE and will only refer to those bits that are nonzero in MASK.
   If other bits are being computed or if masking operations are done
   that select a superset of the bits in MASK, they can sometimes be
   ignored.

   Return a possibly simplified expression, but always convert X to
   MODE.  If X is a CONST_INT, AND the CONST_INT with MASK.

   If JUST_SELECT is nonzero, don't optimize by noticing that bits in MASK
   are all off in X.  This is used when X will be complemented, by either
   NOT, NEG, or XOR.  */

static rtx
force_to_mode (rtx x, machine_mode mode, unsigned HOST_WIDE_INT mask,
	       int just_select)
{
  enum rtx_code code = GET_CODE (x);
  int next_select = just_select || code == XOR || code == NOT || code == NEG;
  machine_mode op_mode;
  unsigned HOST_WIDE_INT nonzero;

  /* If this is a CALL or ASM_OPERANDS, don't do anything.  Some of the
     code below will do the wrong thing since the mode of such an
     expression is VOIDmode.

     Also do nothing if X is a CLOBBER; this can happen if X was
     the return value from a call to gen_lowpart.  */
  if (code == CALL || code == ASM_OPERANDS || code == CLOBBER)
    return x;

  /* We want to perform the operation in its present mode unless we know
     that the operation is valid in MODE, in which case we do the operation
     in MODE.  */
  op_mode = ((GET_MODE_CLASS (mode) == GET_MODE_CLASS (GET_MODE (x))
	      && have_insn_for (code, mode))
	     ? mode : GET_MODE (x));

  /* It is not valid to do a right-shift in a narrower mode
     than the one it came in with.  */
  if ((code == LSHIFTRT || code == ASHIFTRT)
      && partial_subreg_p (mode, GET_MODE (x)))
    op_mode = GET_MODE (x);

  /* Truncate MASK to fit OP_MODE.  */
  if (op_mode)
    mask &= GET_MODE_MASK (op_mode);

  /* Determine what bits of X are guaranteed to be (non)zero.  */
  nonzero = nonzero_bits (x, mode);

  /* If none of the bits in X are needed, return a zero.  */
  if (!just_select && (nonzero & mask) == 0 && !side_effects_p (x))
    x = const0_rtx;

  /* If X is a CONST_INT, return a new one.  Do this here since the
     test below will fail.  */
  if (CONST_INT_P (x))
    {
      if (SCALAR_INT_MODE_P (mode))
	return gen_int_mode (INTVAL (x) & mask, mode);
      else
	{
	  x = GEN_INT (INTVAL (x) & mask);
	  return gen_lowpart_common (mode, x);
	}
    }

  /* If X is narrower than MODE and we want all the bits in X's mode, just
     get X in the proper mode.  */
  if (paradoxical_subreg_p (mode, GET_MODE (x))
      && (GET_MODE_MASK (GET_MODE (x)) & ~mask) == 0)
    return gen_lowpart (mode, x);

  /* We can ignore the effect of a SUBREG if it narrows the mode or
     if the constant masks to zero all the bits the mode doesn't have.  */
  if (GET_CODE (x) == SUBREG
      && subreg_lowpart_p (x)
      && (partial_subreg_p (x)
	  || (mask
	      & GET_MODE_MASK (GET_MODE (x))
	      & ~GET_MODE_MASK (GET_MODE (SUBREG_REG (x)))) == 0))
    return force_to_mode (SUBREG_REG (x), mode, mask, next_select);

  scalar_int_mode int_mode, xmode;
  if (is_a <scalar_int_mode> (mode, &int_mode)
      && is_a <scalar_int_mode> (GET_MODE (x), &xmode))
    /* OP_MODE is either MODE or XMODE, so it must be a scalar
       integer too.  */
    return force_int_to_mode (x, int_mode, xmode,
			      as_a <scalar_int_mode> (op_mode),
			      mask, just_select);

  return gen_lowpart_or_truncate (mode, x);
}

/* Subroutine of force_to_mode that handles cases in which both X and
   the result are scalar integers.  MODE is the mode of the result,
   XMODE is the mode of X, and OP_MODE says which of MODE or XMODE
   is preferred for simplified versions of X.  The other arguments
   are as for force_to_mode.  */

static rtx
force_int_to_mode (rtx x, scalar_int_mode mode, scalar_int_mode xmode,
		   scalar_int_mode op_mode, unsigned HOST_WIDE_INT mask,
		   int just_select)
{
  enum rtx_code code = GET_CODE (x);
  int next_select = just_select || code == XOR || code == NOT || code == NEG;
  unsigned HOST_WIDE_INT fuller_mask;
  rtx op0, op1, temp;
  poly_int64 const_op0;

  /* When we have an arithmetic operation, or a shift whose count we
     do not know, we need to assume that all bits up to the highest-order
     bit in MASK will be needed.  This is how we form such a mask.  */
  if (mask & (HOST_WIDE_INT_1U << (HOST_BITS_PER_WIDE_INT - 1)))
    fuller_mask = HOST_WIDE_INT_M1U;
  else
    fuller_mask = ((HOST_WIDE_INT_1U << (floor_log2 (mask) + 1))
		   - 1);

  switch (code)
    {
    case CLOBBER:
      /* If X is a (clobber (const_int)), return it since we know we are
	 generating something that won't match.  */
      return x;

    case SIGN_EXTEND:
    case ZERO_EXTEND:
    case ZERO_EXTRACT:
    case SIGN_EXTRACT:
      x = expand_compound_operation (x);
      if (GET_CODE (x) != code)
	return force_to_mode (x, mode, mask, next_select);
      break;

    case TRUNCATE:
      /* Similarly for a truncate.  */
      return force_to_mode (XEXP (x, 0), mode, mask, next_select);

    case AND:
      /* If this is an AND with a constant, convert it into an AND
	 whose constant is the AND of that constant with MASK.  If it
	 remains an AND of MASK, delete it since it is redundant.  */

      if (CONST_INT_P (XEXP (x, 1)))
	{
	  x = simplify_and_const_int (x, op_mode, XEXP (x, 0),
				      mask & INTVAL (XEXP (x, 1)));
	  xmode = op_mode;

	  /* If X is still an AND, see if it is an AND with a mask that
	     is just some low-order bits.  If so, and it is MASK, we don't
	     need it.  */

	  if (GET_CODE (x) == AND && CONST_INT_P (XEXP (x, 1))
	      && (INTVAL (XEXP (x, 1)) & GET_MODE_MASK (xmode)) == mask)
	    x = XEXP (x, 0);

	  /* If it remains an AND, try making another AND with the bits
	     in the mode mask that aren't in MASK turned on.  If the
	     constant in the AND is wide enough, this might make a
	     cheaper constant.  */

	  if (GET_CODE (x) == AND && CONST_INT_P (XEXP (x, 1))
	      && GET_MODE_MASK (xmode) != mask
	      && HWI_COMPUTABLE_MODE_P (xmode))
	    {
	      unsigned HOST_WIDE_INT cval
		= UINTVAL (XEXP (x, 1)) | (GET_MODE_MASK (xmode) & ~mask);
	      rtx y;

	      y = simplify_gen_binary (AND, xmode, XEXP (x, 0),
				       gen_int_mode (cval, xmode));
	      if (set_src_cost (y, xmode, optimize_this_for_speed_p)
		  < set_src_cost (x, xmode, optimize_this_for_speed_p))
		x = y;
	    }

	  break;
	}

      goto binop;

    case PLUS:
      /* In (and (plus FOO C1) M), if M is a mask that just turns off
	 low-order bits (as in an alignment operation) and FOO is already
	 aligned to that boundary, mask C1 to that boundary as well.
	 This may eliminate that PLUS and, later, the AND.  */

      {
	unsigned int width = GET_MODE_PRECISION (mode);
	unsigned HOST_WIDE_INT smask = mask;

	/* If MODE is narrower than HOST_WIDE_INT and mask is a negative
	   number, sign extend it.  */

	if (width < HOST_BITS_PER_WIDE_INT
	    && (smask & (HOST_WIDE_INT_1U << (width - 1))) != 0)
	  smask |= HOST_WIDE_INT_M1U << width;

	if (CONST_INT_P (XEXP (x, 1))
	    && pow2p_hwi (- smask)
	    && (nonzero_bits (XEXP (x, 0), mode) & ~smask) == 0
	    && (INTVAL (XEXP (x, 1)) & ~smask) != 0)
	  return force_to_mode (plus_constant (xmode, XEXP (x, 0),
					       (INTVAL (XEXP (x, 1)) & smask)),
				mode, smask, next_select);
      }

      /* fall through */

    case MULT:
      /* Substituting into the operands of a widening MULT is not likely to
	 create RTL matching a machine insn.  */
      if (code == MULT
	  && (GET_CODE (XEXP (x, 0)) == ZERO_EXTEND
	      || GET_CODE (XEXP (x, 0)) == SIGN_EXTEND)
	  && (GET_CODE (XEXP (x, 1)) == ZERO_EXTEND
	      || GET_CODE (XEXP (x, 1)) == SIGN_EXTEND)
	  && REG_P (XEXP (XEXP (x, 0), 0))
	  && REG_P (XEXP (XEXP (x, 1), 0)))
	return gen_lowpart_or_truncate (mode, x);

      /* For PLUS, MINUS and MULT, we need any bits less significant than the
	 most significant bit in MASK since carries from those bits will
	 affect the bits we are interested in.  */
      mask = fuller_mask;
      goto binop;

    case MINUS:
      /* If X is (minus C Y) where C's least set bit is larger than any bit
	 in the mask, then we may replace with (neg Y).  */
      if (poly_int_rtx_p (XEXP (x, 0), &const_op0)
	  && (unsigned HOST_WIDE_INT) known_alignment (const_op0) > mask)
	{
	  x = simplify_gen_unary (NEG, xmode, XEXP (x, 1), xmode);
	  return force_to_mode (x, mode, mask, next_select);
	}

      /* Similarly, if C contains every bit in the fuller_mask, then we may
	 replace with (not Y).  */
      if (CONST_INT_P (XEXP (x, 0))
	  && ((UINTVAL (XEXP (x, 0)) | fuller_mask) == UINTVAL (XEXP (x, 0))))
	{
	  x = simplify_gen_unary (NOT, xmode, XEXP (x, 1), xmode);
	  return force_to_mode (x, mode, mask, next_select);
	}

      mask = fuller_mask;
      goto binop;

    case IOR:
    case XOR:
      /* If X is (ior (lshiftrt FOO C1) C2), try to commute the IOR and
	 LSHIFTRT so we end up with an (and (lshiftrt (ior ...) ...) ...)
	 operation which may be a bitfield extraction.  Ensure that the
	 constant we form is not wider than the mode of X.  */

      if (GET_CODE (XEXP (x, 0)) == LSHIFTRT
	  && CONST_INT_P (XEXP (XEXP (x, 0), 1))
	  && INTVAL (XEXP (XEXP (x, 0), 1)) >= 0
	  && INTVAL (XEXP (XEXP (x, 0), 1)) < HOST_BITS_PER_WIDE_INT
	  && CONST_INT_P (XEXP (x, 1))
	  && ((INTVAL (XEXP (XEXP (x, 0), 1))
	       + floor_log2 (INTVAL (XEXP (x, 1))))
	      < GET_MODE_PRECISION (xmode))
	  && (UINTVAL (XEXP (x, 1))
	      & ~nonzero_bits (XEXP (x, 0), xmode)) == 0)
	{
	  temp = gen_int_mode ((INTVAL (XEXP (x, 1)) & mask)
			       << INTVAL (XEXP (XEXP (x, 0), 1)),
			       xmode);
	  temp = simplify_gen_binary (GET_CODE (x), xmode,
				      XEXP (XEXP (x, 0), 0), temp);
	  x = simplify_gen_binary (LSHIFTRT, xmode, temp,
				   XEXP (XEXP (x, 0), 1));
	  return force_to_mode (x, mode, mask, next_select);
	}

    binop:
      /* For most binary operations, just propagate into the operation and
	 change the mode if we have an operation of that mode.  */

      op0 = force_to_mode (XEXP (x, 0), mode, mask, next_select);
      op1 = force_to_mode (XEXP (x, 1), mode, mask, next_select);

      /* If we ended up truncating both operands, truncate the result of the
	 operation instead.  */
      if (GET_CODE (op0) == TRUNCATE
	  && GET_CODE (op1) == TRUNCATE)
	{
	  op0 = XEXP (op0, 0);
	  op1 = XEXP (op1, 0);
	}

      op0 = gen_lowpart_or_truncate (op_mode, op0);
      op1 = gen_lowpart_or_truncate (op_mode, op1);

      if (op_mode != xmode || op0 != XEXP (x, 0) || op1 != XEXP (x, 1))
	{
	  x = simplify_gen_binary (code, op_mode, op0, op1);
	  xmode = op_mode;
	}
      break;

    case ASHIFT:
      /* For left shifts, do the same, but just for the first operand.
	 However, we cannot do anything with shifts where we cannot
	 guarantee that the counts are smaller than the size of the mode
	 because such a count will have a different meaning in a
	 wider mode.  */

      if (! (CONST_INT_P (XEXP (x, 1))
	     && INTVAL (XEXP (x, 1)) >= 0
	     && INTVAL (XEXP (x, 1)) < GET_MODE_PRECISION (mode))
	  && ! (GET_MODE (XEXP (x, 1)) != VOIDmode
		&& (nonzero_bits (XEXP (x, 1), GET_MODE (XEXP (x, 1)))
		    < (unsigned HOST_WIDE_INT) GET_MODE_PRECISION (mode))))
	break;

      /* If the shift count is a constant and we can do arithmetic in
	 the mode of the shift, refine which bits we need.  Otherwise, use the
	 conservative form of the mask.  */
      if (CONST_INT_P (XEXP (x, 1))
	  && INTVAL (XEXP (x, 1)) >= 0
	  && INTVAL (XEXP (x, 1)) < GET_MODE_PRECISION (op_mode)
	  && HWI_COMPUTABLE_MODE_P (op_mode))
	mask >>= INTVAL (XEXP (x, 1));
      else
	mask = fuller_mask;

      op0 = gen_lowpart_or_truncate (op_mode,
				     force_to_mode (XEXP (x, 0), mode,
						    mask, next_select));

      if (op_mode != xmode || op0 != XEXP (x, 0))
	{
	  x = simplify_gen_binary (code, op_mode, op0, XEXP (x, 1));
	  xmode = op_mode;
	}
      break;

    case LSHIFTRT:
      /* Here we can only do something if the shift count is a constant,
	 this shift constant is valid for the host, and we can do arithmetic
	 in OP_MODE.  */

      if (CONST_INT_P (XEXP (x, 1))
	  && INTVAL (XEXP (x, 1)) >= 0
	  && INTVAL (XEXP (x, 1)) < HOST_BITS_PER_WIDE_INT
	  && HWI_COMPUTABLE_MODE_P (op_mode))
	{
	  rtx inner = XEXP (x, 0);
	  unsigned HOST_WIDE_INT inner_mask;

	  /* Select the mask of the bits we need for the shift operand.  */
	  inner_mask = mask << INTVAL (XEXP (x, 1));

	  /* We can only change the mode of the shift if we can do arithmetic
	     in the mode of the shift and INNER_MASK is no wider than the
	     width of X's mode.  */
	  if ((inner_mask & ~GET_MODE_MASK (xmode)) != 0)
	    op_mode = xmode;

	  inner = force_to_mode (inner, op_mode, inner_mask, next_select);

	  if (xmode != op_mode || inner != XEXP (x, 0))
	    {
	      x = simplify_gen_binary (LSHIFTRT, op_mode, inner, XEXP (x, 1));
	      xmode = op_mode;
	    }
	}

      /* If we have (and (lshiftrt FOO C1) C2) where the combination of the
	 shift and AND produces only copies of the sign bit (C2 is one less
	 than a power of two), we can do this with just a shift.  */

      if (GET_CODE (x) == LSHIFTRT
	  && CONST_INT_P (XEXP (x, 1))
	  /* The shift puts one of the sign bit copies in the least significant
	     bit.  */
	  && ((INTVAL (XEXP (x, 1))
	       + num_sign_bit_copies (XEXP (x, 0), GET_MODE (XEXP (x, 0))))
	      >= GET_MODE_PRECISION (xmode))
	  && pow2p_hwi (mask + 1)
	  /* Number of bits left after the shift must be more than the mask
	     needs.  */
	  && ((INTVAL (XEXP (x, 1)) + exact_log2 (mask + 1))
	      <= GET_MODE_PRECISION (xmode))
	  /* Must be more sign bit copies than the mask needs.  */
	  && ((int) num_sign_bit_copies (XEXP (x, 0), GET_MODE (XEXP (x, 0)))
	      >= exact_log2 (mask + 1)))
	{
	  int nbits = GET_MODE_PRECISION (xmode) - exact_log2 (mask + 1);
	  x = simplify_gen_binary (LSHIFTRT, xmode, XEXP (x, 0),
				   gen_int_shift_amount (xmode, nbits));
	}
      goto shiftrt;

    case ASHIFTRT:
      /* If we are just looking for the sign bit, we don't need this shift at
	 all, even if it has a variable count.  */
      if (val_signbit_p (xmode, mask))
	return force_to_mode (XEXP (x, 0), mode, mask, next_select);

      /* If this is a shift by a constant, get a mask that contains those bits
	 that are not copies of the sign bit.  We then have two cases:  If
	 MASK only includes those bits, this can be a logical shift, which may
	 allow simplifications.  If MASK is a single-bit field not within
	 those bits, we are requesting a copy of the sign bit and hence can
	 shift the sign bit to the appropriate location.  */

      if (CONST_INT_P (XEXP (x, 1)) && INTVAL (XEXP (x, 1)) >= 0
	  && INTVAL (XEXP (x, 1)) < HOST_BITS_PER_WIDE_INT)
	{
	  unsigned HOST_WIDE_INT nonzero;
	  int i;

	  /* If the considered data is wider than HOST_WIDE_INT, we can't
	     represent a mask for all its bits in a single scalar.
	     But we only care about the lower bits, so calculate these.  */

	  if (GET_MODE_PRECISION (xmode) > HOST_BITS_PER_WIDE_INT)
	    {
	      nonzero = HOST_WIDE_INT_M1U;

	      /* GET_MODE_PRECISION (GET_MODE (x)) - INTVAL (XEXP (x, 1))
		 is the number of bits a full-width mask would have set.
		 We need only shift if these are fewer than nonzero can
		 hold.  If not, we must keep all bits set in nonzero.  */

	      if (GET_MODE_PRECISION (xmode) - INTVAL (XEXP (x, 1))
		  < HOST_BITS_PER_WIDE_INT)
		nonzero >>= INTVAL (XEXP (x, 1))
			    + HOST_BITS_PER_WIDE_INT
			    - GET_MODE_PRECISION (xmode);
	    }
	  else
	    {
	      nonzero = GET_MODE_MASK (xmode);
	      nonzero >>= INTVAL (XEXP (x, 1));
	    }

	  if ((mask & ~nonzero) == 0)
	    {
	      x = simplify_shift_const (NULL_RTX, LSHIFTRT, xmode,
					XEXP (x, 0), INTVAL (XEXP (x, 1)));
	      if (GET_CODE (x) != ASHIFTRT)
		return force_to_mode (x, mode, mask, next_select);
	    }

	  else if ((i = exact_log2 (mask)) >= 0)
	    {
	      x = simplify_shift_const
		  (NULL_RTX, LSHIFTRT, xmode, XEXP (x, 0),
		   GET_MODE_PRECISION (xmode) - 1 - i);

	      if (GET_CODE (x) != ASHIFTRT)
		return force_to_mode (x, mode, mask, next_select);
	    }
	}

      /* If MASK is 1, convert this to an LSHIFTRT.  This can be done
	 even if the shift count isn't a constant.  */
      if (mask == 1)
	x = simplify_gen_binary (LSHIFTRT, xmode, XEXP (x, 0), XEXP (x, 1));

    shiftrt:

      /* If this is a zero- or sign-extension operation that just affects bits
	 we don't care about, remove it.  Be sure the call above returned
	 something that is still a shift.  */

      if ((GET_CODE (x) == LSHIFTRT || GET_CODE (x) == ASHIFTRT)
	  && CONST_INT_P (XEXP (x, 1))
	  && INTVAL (XEXP (x, 1)) >= 0
	  && (INTVAL (XEXP (x, 1))
	      <= GET_MODE_PRECISION (xmode) - (floor_log2 (mask) + 1))
	  && GET_CODE (XEXP (x, 0)) == ASHIFT
	  && XEXP (XEXP (x, 0), 1) == XEXP (x, 1))
	return force_to_mode (XEXP (XEXP (x, 0), 0), mode, mask,
			      next_select);

      break;

    case ROTATE:
    case ROTATERT:
      /* If the shift count is constant and we can do computations
	 in the mode of X, compute where the bits we care about are.
	 Otherwise, we can't do anything.  Don't change the mode of
	 the shift or propagate MODE into the shift, though.  */
      if (CONST_INT_P (XEXP (x, 1))
	  && INTVAL (XEXP (x, 1)) >= 0)
	{
	  temp = simplify_binary_operation (code == ROTATE ? ROTATERT : ROTATE,
					    xmode, gen_int_mode (mask, xmode),
					    XEXP (x, 1));
	  if (temp && CONST_INT_P (temp))
	    x = simplify_gen_binary (code, xmode,
				     force_to_mode (XEXP (x, 0), xmode,
						    INTVAL (temp), next_select),
				     XEXP (x, 1));
	}
      break;

    case NEG:
      /* If we just want the low-order bit, the NEG isn't needed since it
	 won't change the low-order bit.  */
      if (mask == 1)
	return force_to_mode (XEXP (x, 0), mode, mask, just_select);

      /* We need any bits less significant than the most significant bit in
	 MASK since carries from those bits will affect the bits we are
	 interested in.  */
      mask = fuller_mask;
      goto unop;

    case NOT:
      /* (not FOO) is (xor FOO CONST), so if FOO is an LSHIFTRT, we can do the
	 same as the XOR case above.  Ensure that the constant we form is not
	 wider than the mode of X.  */

      if (GET_CODE (XEXP (x, 0)) == LSHIFTRT
	  && CONST_INT_P (XEXP (XEXP (x, 0), 1))
	  && INTVAL (XEXP (XEXP (x, 0), 1)) >= 0
	  && (INTVAL (XEXP (XEXP (x, 0), 1)) + floor_log2 (mask)
	      < GET_MODE_PRECISION (xmode))
	  && INTVAL (XEXP (XEXP (x, 0), 1)) < HOST_BITS_PER_WIDE_INT)
	{
	  temp = gen_int_mode (mask << INTVAL (XEXP (XEXP (x, 0), 1)), xmode);
	  temp = simplify_gen_binary (XOR, xmode, XEXP (XEXP (x, 0), 0), temp);
	  x = simplify_gen_binary (LSHIFTRT, xmode,
				   temp, XEXP (XEXP (x, 0), 1));

	  return force_to_mode (x, mode, mask, next_select);
	}

      /* (and (not FOO) CONST) is (not (or FOO (not CONST))), so we must
	 use the full mask inside the NOT.  */
      mask = fuller_mask;

    unop:
      op0 = gen_lowpart_or_truncate (op_mode,
				     force_to_mode (XEXP (x, 0), mode, mask,
						    next_select));
      if (op_mode != xmode || op0 != XEXP (x, 0))
	{
	  x = simplify_gen_unary (code, op_mode, op0, op_mode);
	  xmode = op_mode;
	}
      break;

    case NE:
      /* (and (ne FOO 0) CONST) can be (and FOO CONST) if CONST is included
	 in STORE_FLAG_VALUE and FOO has a single bit that might be nonzero,
	 which is equal to STORE_FLAG_VALUE.  */
      if ((mask & ~STORE_FLAG_VALUE) == 0
	  && XEXP (x, 1) == const0_rtx
	  && GET_MODE (XEXP (x, 0)) == mode
	  && pow2p_hwi (nonzero_bits (XEXP (x, 0), mode))
	  && (nonzero_bits (XEXP (x, 0), mode)
	      == (unsigned HOST_WIDE_INT) STORE_FLAG_VALUE))
	return force_to_mode (XEXP (x, 0), mode, mask, next_select);

      break;

    case IF_THEN_ELSE:
      /* We have no way of knowing if the IF_THEN_ELSE can itself be
	 written in a narrower mode.  We play it safe and do not do so.  */

      op0 = gen_lowpart_or_truncate (xmode,
				     force_to_mode (XEXP (x, 1), mode,
						    mask, next_select));
      op1 = gen_lowpart_or_truncate (xmode,
				     force_to_mode (XEXP (x, 2), mode,
						    mask, next_select));
      if (op0 != XEXP (x, 1) || op1 != XEXP (x, 2))
	x = simplify_gen_ternary (IF_THEN_ELSE, xmode,
				  GET_MODE (XEXP (x, 0)), XEXP (x, 0),
				  op0, op1);
      break;

    default:
      break;
    }

  /* Ensure we return a value of the proper mode.  */
  return gen_lowpart_or_truncate (mode, x);
}

/* Return nonzero if X is an expression that has one of two values depending on
   whether some other value is zero or nonzero.  In that case, we return the
   value that is being tested, *PTRUE is set to the value if the rtx being
   returned has a nonzero value, and *PFALSE is set to the other alternative.

   If we return zero, we set *PTRUE and *PFALSE to X.  */

static rtx
if_then_else_cond (rtx x, rtx *ptrue, rtx *pfalse)
{
  machine_mode mode = GET_MODE (x);
  enum rtx_code code = GET_CODE (x);
  rtx cond0, cond1, true0, true1, false0, false1;
  unsigned HOST_WIDE_INT nz;
  scalar_int_mode int_mode;

  /* If we are comparing a value against zero, we are done.  */
  if ((code == NE || code == EQ)
      && XEXP (x, 1) == const0_rtx)
    {
      *ptrue = (code == NE) ? const_true_rtx : const0_rtx;
      *pfalse = (code == NE) ? const0_rtx : const_true_rtx;
      return XEXP (x, 0);
    }

  /* If this is a unary operation whose operand has one of two values, apply
     our opcode to compute those values.  */
  else if (UNARY_P (x)
	   && (cond0 = if_then_else_cond (XEXP (x, 0), &true0, &false0)) != 0)
    {
      *ptrue = simplify_gen_unary (code, mode, true0, GET_MODE (XEXP (x, 0)));
      *pfalse = simplify_gen_unary (code, mode, false0,
				    GET_MODE (XEXP (x, 0)));
      return cond0;
    }

  /* If this is a COMPARE, do nothing, since the IF_THEN_ELSE we would
     make can't possibly match and would suppress other optimizations.  */
  else if (code == COMPARE)
    ;

  /* If this is a binary operation, see if either side has only one of two
     values.  If either one does or if both do and they are conditional on
     the same value, compute the new true and false values.  */
  else if (BINARY_P (x))
    {
      rtx op0 = XEXP (x, 0);
      rtx op1 = XEXP (x, 1);
      cond0 = if_then_else_cond (op0, &true0, &false0);
      cond1 = if_then_else_cond (op1, &true1, &false1);

      if ((cond0 != 0 && cond1 != 0 && !rtx_equal_p (cond0, cond1))
	  && (REG_P (op0) || REG_P (op1)))
	{
	  /* Try to enable a simplification by undoing work done by
	     if_then_else_cond if it converted a REG into something more
	     complex.  */
	  if (REG_P (op0))
	    {
	      cond0 = 0;
	      true0 = false0 = op0;
	    }
	  else
	    {
	      cond1 = 0;
	      true1 = false1 = op1;
	    }
	}

      if ((cond0 != 0 || cond1 != 0)
	  && ! (cond0 != 0 && cond1 != 0 && !rtx_equal_p (cond0, cond1)))
	{
	  /* If if_then_else_cond returned zero, then true/false are the
	     same rtl.  We must copy one of them to prevent invalid rtl
	     sharing.  */
	  if (cond0 == 0)
	    true0 = copy_rtx (true0);
	  else if (cond1 == 0)
	    true1 = copy_rtx (true1);

	  if (COMPARISON_P (x))
	    {
	      *ptrue = simplify_gen_relational (code, mode, VOIDmode,
						true0, true1);
	      *pfalse = simplify_gen_relational (code, mode, VOIDmode,
						 false0, false1);
	     }
	  else
	    {
	      *ptrue = simplify_gen_binary (code, mode, true0, true1);
	      *pfalse = simplify_gen_binary (code, mode, false0, false1);
	    }

	  return cond0 ? cond0 : cond1;
	}

      /* See if we have PLUS, IOR, XOR, MINUS or UMAX, where one of the
	 operands is zero when the other is nonzero, and vice-versa,
	 and STORE_FLAG_VALUE is 1 or -1.  */

      if ((STORE_FLAG_VALUE == 1 || STORE_FLAG_VALUE == -1)
	  && (code == PLUS || code == IOR || code == XOR || code == MINUS
	      || code == UMAX)
	  && GET_CODE (XEXP (x, 0)) == MULT && GET_CODE (XEXP (x, 1)) == MULT)
	{
	  rtx op0 = XEXP (XEXP (x, 0), 1);
	  rtx op1 = XEXP (XEXP (x, 1), 1);

	  cond0 = XEXP (XEXP (x, 0), 0);
	  cond1 = XEXP (XEXP (x, 1), 0);

	  if (COMPARISON_P (cond0)
	      && COMPARISON_P (cond1)
	      && SCALAR_INT_MODE_P (mode)
	      && ((GET_CODE (cond0) == reversed_comparison_code (cond1, NULL)
		   && rtx_equal_p (XEXP (cond0, 0), XEXP (cond1, 0))
		   && rtx_equal_p (XEXP (cond0, 1), XEXP (cond1, 1)))
		  || ((swap_condition (GET_CODE (cond0))
		       == reversed_comparison_code (cond1, NULL))
		      && rtx_equal_p (XEXP (cond0, 0), XEXP (cond1, 1))
		      && rtx_equal_p (XEXP (cond0, 1), XEXP (cond1, 0))))
	      && ! side_effects_p (x))
	    {
	      *ptrue = simplify_gen_binary (MULT, mode, op0, const_true_rtx);
	      *pfalse = simplify_gen_binary (MULT, mode,
					     (code == MINUS
					      ? simplify_gen_unary (NEG, mode,
								    op1, mode)
					      : op1),
					      const_true_rtx);
	      return cond0;
	    }
	}

      /* Similarly for MULT, AND and UMIN, except that for these the result
	 is always zero.  */
      if ((STORE_FLAG_VALUE == 1 || STORE_FLAG_VALUE == -1)
	  && (code == MULT || code == AND || code == UMIN)
	  && GET_CODE (XEXP (x, 0)) == MULT && GET_CODE (XEXP (x, 1)) == MULT)
	{
	  cond0 = XEXP (XEXP (x, 0), 0);
	  cond1 = XEXP (XEXP (x, 1), 0);

	  if (COMPARISON_P (cond0)
	      && COMPARISON_P (cond1)
	      && ((GET_CODE (cond0) == reversed_comparison_code (cond1, NULL)
		   && rtx_equal_p (XEXP (cond0, 0), XEXP (cond1, 0))
		   && rtx_equal_p (XEXP (cond0, 1), XEXP (cond1, 1)))
		  || ((swap_condition (GET_CODE (cond0))
		       == reversed_comparison_code (cond1, NULL))
		      && rtx_equal_p (XEXP (cond0, 0), XEXP (cond1, 1))
		      && rtx_equal_p (XEXP (cond0, 1), XEXP (cond1, 0))))
	      && ! side_effects_p (x))
	    {
	      *ptrue = *pfalse = const0_rtx;
	      return cond0;
	    }
	}
    }

  else if (code == IF_THEN_ELSE)
    {
      /* If we have IF_THEN_ELSE already, extract the condition and
	 canonicalize it if it is NE or EQ.  */
      cond0 = XEXP (x, 0);
      *ptrue = XEXP (x, 1), *pfalse = XEXP (x, 2);
      if (GET_CODE (cond0) == NE && XEXP (cond0, 1) == const0_rtx)
	return XEXP (cond0, 0);
      else if (GET_CODE (cond0) == EQ && XEXP (cond0, 1) == const0_rtx)
	{
	  *ptrue = XEXP (x, 2), *pfalse = XEXP (x, 1);
	  return XEXP (cond0, 0);
	}
      else
	return cond0;
    }

  /* If X is a SUBREG, we can narrow both the true and false values
     if the inner expression, if there is a condition.  */
  else if (code == SUBREG
	   && (cond0 = if_then_else_cond (SUBREG_REG (x), &true0,
					  &false0)) != 0)
    {
      true0 = simplify_gen_subreg (mode, true0,
				   GET_MODE (SUBREG_REG (x)), SUBREG_BYTE (x));
      false0 = simplify_gen_subreg (mode, false0,
				    GET_MODE (SUBREG_REG (x)), SUBREG_BYTE (x));
      if (true0 && false0)
	{
	  *ptrue = true0;
	  *pfalse = false0;
	  return cond0;
	}
    }

  /* If X is a constant, this isn't special and will cause confusions
     if we treat it as such.  Likewise if it is equivalent to a constant.  */
  else if (CONSTANT_P (x)
	   || ((cond0 = get_last_value (x)) != 0 && CONSTANT_P (cond0)))
    ;

  /* If we're in BImode, canonicalize on 0 and STORE_FLAG_VALUE, as that
     will be least confusing to the rest of the compiler.  */
  else if (mode == BImode)
    {
      *ptrue = GEN_INT (STORE_FLAG_VALUE), *pfalse = const0_rtx;
      return x;
    }

  /* If X is known to be either 0 or -1, those are the true and
     false values when testing X.  */
  else if (x == constm1_rtx || x == const0_rtx
	   || (is_a <scalar_int_mode> (mode, &int_mode)
	       && (num_sign_bit_copies (x, int_mode)
		   == GET_MODE_PRECISION (int_mode))))
    {
      *ptrue = constm1_rtx, *pfalse = const0_rtx;
      return x;
    }

  /* Likewise for 0 or a single bit.  */
  else if (HWI_COMPUTABLE_MODE_P (mode)
	   && pow2p_hwi (nz = nonzero_bits (x, mode)))
    {
      *ptrue = gen_int_mode (nz, mode), *pfalse = const0_rtx;
      return x;
    }

  /* Otherwise fail; show no condition with true and false values the same.  */
  *ptrue = *pfalse = x;
  return 0;
}

/* Return the value of expression X given the fact that condition COND
   is known to be true when applied to REG as its first operand and VAL
   as its second.  X is known to not be shared and so can be modified in
   place.

   We only handle the simplest cases, and specifically those cases that
   arise with IF_THEN_ELSE expressions.  */

static rtx
known_cond (rtx x, enum rtx_code cond, rtx reg, rtx val)
{
  enum rtx_code code = GET_CODE (x);
  const char *fmt;
  int i, j;

  if (side_effects_p (x))
    return x;

  /* If either operand of the condition is a floating point value,
     then we have to avoid collapsing an EQ comparison.  */
  if (cond == EQ
      && rtx_equal_p (x, reg)
      && ! FLOAT_MODE_P (GET_MODE (x))
      && ! FLOAT_MODE_P (GET_MODE (val)))
    return val;

  if (cond == UNEQ && rtx_equal_p (x, reg))
    return val;

  /* If X is (abs REG) and we know something about REG's relationship
     with zero, we may be able to simplify this.  */

  if (code == ABS && rtx_equal_p (XEXP (x, 0), reg) && val == const0_rtx)
    switch (cond)
      {
      case GE:  case GT:  case EQ:
	return XEXP (x, 0);
      case LT:  case LE:
	return simplify_gen_unary (NEG, GET_MODE (XEXP (x, 0)),
				   XEXP (x, 0),
				   GET_MODE (XEXP (x, 0)));
      default:
	break;
      }

  /* The only other cases we handle are MIN, MAX, and comparisons if the
     operands are the same as REG and VAL.  */

  else if (COMPARISON_P (x) || COMMUTATIVE_ARITH_P (x))
    {
      if (rtx_equal_p (XEXP (x, 0), val))
        {
	  std::swap (val, reg);
	  cond = swap_condition (cond);
        }

      if (rtx_equal_p (XEXP (x, 0), reg) && rtx_equal_p (XEXP (x, 1), val))
	{
	  if (COMPARISON_P (x))
	    {
	      if (comparison_dominates_p (cond, code))
		return VECTOR_MODE_P (GET_MODE (x)) ? x : const_true_rtx;

	      code = reversed_comparison_code (x, NULL);
	      if (code != UNKNOWN
		  && comparison_dominates_p (cond, code))
		return CONST0_RTX (GET_MODE (x));
	      else
		return x;
	    }
	  else if (code == SMAX || code == SMIN
		   || code == UMIN || code == UMAX)
	    {
	      int unsignedp = (code == UMIN || code == UMAX);

	      /* Do not reverse the condition when it is NE or EQ.
		 This is because we cannot conclude anything about
		 the value of 'SMAX (x, y)' when x is not equal to y,
		 but we can when x equals y.  */
	      if ((code == SMAX || code == UMAX)
		  && ! (cond == EQ || cond == NE))
		cond = reverse_condition (cond);

	      switch (cond)
		{
		case GE:   case GT:
		  return unsignedp ? x : XEXP (x, 1);
		case LE:   case LT:
		  return unsignedp ? x : XEXP (x, 0);
		case GEU:  case GTU:
		  return unsignedp ? XEXP (x, 1) : x;
		case LEU:  case LTU:
		  return unsignedp ? XEXP (x, 0) : x;
		default:
		  break;
		}
	    }
	}
    }
  else if (code == SUBREG)
    {
      machine_mode inner_mode = GET_MODE (SUBREG_REG (x));
      rtx new_rtx, r = known_cond (SUBREG_REG (x), cond, reg, val);

      if (SUBREG_REG (x) != r)
	{
	  /* We must simplify subreg here, before we lose track of the
	     original inner_mode.  */
	  new_rtx = simplify_subreg (GET_MODE (x), r,
				     inner_mode, SUBREG_BYTE (x));
	  if (new_rtx)
	    return new_rtx;
	  else
	    SUBST (SUBREG_REG (x), r);
	}

      return x;
    }
  /* We don't have to handle SIGN_EXTEND here, because even in the
     case of replacing something with a modeless CONST_INT, a
     CONST_INT is already (supposed to be) a valid sign extension for
     its narrower mode, which implies it's already properly
     sign-extended for the wider mode.  Now, for ZERO_EXTEND, the
     story is different.  */
  else if (code == ZERO_EXTEND)
    {
      machine_mode inner_mode = GET_MODE (XEXP (x, 0));
      rtx new_rtx, r = known_cond (XEXP (x, 0), cond, reg, val);

      if (XEXP (x, 0) != r)
	{
	  /* We must simplify the zero_extend here, before we lose
	     track of the original inner_mode.  */
	  new_rtx = simplify_unary_operation (ZERO_EXTEND, GET_MODE (x),
					      r, inner_mode);
	  if (new_rtx)
	    return new_rtx;
	  else
	    SUBST (XEXP (x, 0), r);
	}

      return x;
    }

  fmt = GET_RTX_FORMAT (code);
  for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
    {
      if (fmt[i] == 'e')
	SUBST (XEXP (x, i), known_cond (XEXP (x, i), cond, reg, val));
      else if (fmt[i] == 'E')
	for (j = XVECLEN (x, i) - 1; j >= 0; j--)
	  SUBST (XVECEXP (x, i, j), known_cond (XVECEXP (x, i, j),
						cond, reg, val));
    }

  return x;
}

/* See if X and Y are equal for the purposes of seeing if we can rewrite an
   assignment as a field assignment.  */

static int
rtx_equal_for_field_assignment_p (rtx x, rtx y, bool widen_x)
{
  if (widen_x && GET_MODE (x) != GET_MODE (y))
    {
      if (paradoxical_subreg_p (GET_MODE (x), GET_MODE (y)))
	return 0;
      if (BYTES_BIG_ENDIAN != WORDS_BIG_ENDIAN)
	return 0;
      x = adjust_address_nv (x, GET_MODE (y),
			     byte_lowpart_offset (GET_MODE (y),
						  GET_MODE (x)));
    }

  if (x == y || rtx_equal_p (x, y))
    return 1;

  if (x == 0 || y == 0 || GET_MODE (x) != GET_MODE (y))
    return 0;

  /* Check for a paradoxical SUBREG of a MEM compared with the MEM.
     Note that all SUBREGs of MEM are paradoxical; otherwise they
     would have been rewritten.  */
  if (MEM_P (x) && GET_CODE (y) == SUBREG
      && MEM_P (SUBREG_REG (y))
      && rtx_equal_p (SUBREG_REG (y),
		      gen_lowpart (GET_MODE (SUBREG_REG (y)), x)))
    return 1;

  if (MEM_P (y) && GET_CODE (x) == SUBREG
      && MEM_P (SUBREG_REG (x))
      && rtx_equal_p (SUBREG_REG (x),
		      gen_lowpart (GET_MODE (SUBREG_REG (x)), y)))
    return 1;

  /* We used to see if get_last_value of X and Y were the same but that's
     not correct.  In one direction, we'll cause the assignment to have
     the wrong destination and in the case, we'll import a register into this
     insn that might have already have been dead.   So fail if none of the
     above cases are true.  */
  return 0;
}

/* See if X, a SET operation, can be rewritten as a bit-field assignment.
   Return that assignment if so.

   We only handle the most common cases.  */

static rtx
make_field_assignment (rtx x)
{
  rtx dest = SET_DEST (x);
  rtx src = SET_SRC (x);
  rtx assign;
  rtx rhs, lhs;
  HOST_WIDE_INT c1;
  HOST_WIDE_INT pos;
  unsigned HOST_WIDE_INT len;
  rtx other;

  /* All the rules in this function are specific to scalar integers.  */
  scalar_int_mode mode;
  if (!is_a <scalar_int_mode> (GET_MODE (dest), &mode))
    return x;

  /* If SRC was (and (not (ashift (const_int 1) POS)) DEST), this is
     a clear of a one-bit field.  We will have changed it to
     (and (rotate (const_int -2) POS) DEST), so check for that.  Also check
     for a SUBREG.  */

  if (GET_CODE (src) == AND && GET_CODE (XEXP (src, 0)) == ROTATE
      && CONST_INT_P (XEXP (XEXP (src, 0), 0))
      && INTVAL (XEXP (XEXP (src, 0), 0)) == -2
      && rtx_equal_for_field_assignment_p (dest, XEXP (src, 1)))
    {
      assign = make_extraction (VOIDmode, dest, 0, XEXP (XEXP (src, 0), 1),
				1, 1, 1, 0);
      if (assign != 0)
	return gen_rtx_SET (assign, const0_rtx);
      return x;
    }

  if (GET_CODE (src) == AND && GET_CODE (XEXP (src, 0)) == SUBREG
      && subreg_lowpart_p (XEXP (src, 0))
      && partial_subreg_p (XEXP (src, 0))
      && GET_CODE (SUBREG_REG (XEXP (src, 0))) == ROTATE
      && CONST_INT_P (XEXP (SUBREG_REG (XEXP (src, 0)), 0))
      && INTVAL (XEXP (SUBREG_REG (XEXP (src, 0)), 0)) == -2
      && rtx_equal_for_field_assignment_p (dest, XEXP (src, 1)))
    {
      assign = make_extraction (VOIDmode, dest, 0,
				XEXP (SUBREG_REG (XEXP (src, 0)), 1),
				1, 1, 1, 0);
      if (assign != 0)
	return gen_rtx_SET (assign, const0_rtx);
      return x;
    }

  /* If SRC is (ior (ashift (const_int 1) POS) DEST), this is a set of a
     one-bit field.  */
  if (GET_CODE (src) == IOR && GET_CODE (XEXP (src, 0)) == ASHIFT
      && XEXP (XEXP (src, 0), 0) == const1_rtx
      && rtx_equal_for_field_assignment_p (dest, XEXP (src, 1)))
    {
      assign = make_extraction (VOIDmode, dest, 0, XEXP (XEXP (src, 0), 1),
				1, 1, 1, 0);
      if (assign != 0)
	return gen_rtx_SET (assign, const1_rtx);
      return x;
    }

  /* If DEST is already a field assignment, i.e. ZERO_EXTRACT, and the
     SRC is an AND with all bits of that field set, then we can discard
     the AND.  */
  if (GET_CODE (dest) == ZERO_EXTRACT
      && CONST_INT_P (XEXP (dest, 1))
      && GET_CODE (src) == AND
      && CONST_INT_P (XEXP (src, 1)))
    {
      HOST_WIDE_INT width = INTVAL (XEXP (dest, 1));
      unsigned HOST_WIDE_INT and_mask = INTVAL (XEXP (src, 1));
      unsigned HOST_WIDE_INT ze_mask;

      if (width >= HOST_BITS_PER_WIDE_INT)
	ze_mask = -1;
      else
	ze_mask = ((unsigned HOST_WIDE_INT)1 << width) - 1;

      /* Complete overlap.  We can remove the source AND.  */
      if ((and_mask & ze_mask) == ze_mask)
	return gen_rtx_SET (dest, XEXP (src, 0));

      /* Partial overlap.  We can reduce the source AND.  */
      if ((and_mask & ze_mask) != and_mask)
	{
	  src = gen_rtx_AND (mode, XEXP (src, 0),
			     gen_int_mode (and_mask & ze_mask, mode));
	  return gen_rtx_SET (dest, src);
	}
    }

  /* The other case we handle is assignments into a constant-position
     field.  They look like (ior/xor (and DEST C1) OTHER).  If C1 represents
     a mask that has all one bits except for a group of zero bits and
     OTHER is known to have zeros where C1 has ones, this is such an
     assignment.  Compute the position and length from C1.  Shift OTHER
     to the appropriate position, force it to the required mode, and
     make the extraction.  Check for the AND in both operands.  */

  /* One or more SUBREGs might obscure the constant-position field
     assignment.  The first one we are likely to encounter is an outer
     narrowing SUBREG, which we can just strip for the purposes of
     identifying the constant-field assignment.  */
  scalar_int_mode src_mode = mode;
  if (GET_CODE (src) == SUBREG
      && subreg_lowpart_p (src)
      && is_a <scalar_int_mode> (GET_MODE (SUBREG_REG (src)), &src_mode))
    src = SUBREG_REG (src);

  if (GET_CODE (src) != IOR && GET_CODE (src) != XOR)
    return x;

  rhs = expand_compound_operation (XEXP (src, 0));
  lhs = expand_compound_operation (XEXP (src, 1));

  if (GET_CODE (rhs) == AND
      && CONST_INT_P (XEXP (rhs, 1))
      && rtx_equal_for_field_assignment_p (XEXP (rhs, 0), dest))
    c1 = INTVAL (XEXP (rhs, 1)), other = lhs;
  /* The second SUBREG that might get in the way is a paradoxical
     SUBREG around the first operand of the AND.  We want to 
     pretend the operand is as wide as the destination here.   We
     do this by adjusting the MEM to wider mode for the sole
     purpose of the call to rtx_equal_for_field_assignment_p.   Also
     note this trick only works for MEMs.  */
  else if (GET_CODE (rhs) == AND
	   && paradoxical_subreg_p (XEXP (rhs, 0))
	   && MEM_P (SUBREG_REG (XEXP (rhs, 0)))
	   && CONST_INT_P (XEXP (rhs, 1))
	   && rtx_equal_for_field_assignment_p (SUBREG_REG (XEXP (rhs, 0)),
						dest, true))
    c1 = INTVAL (XEXP (rhs, 1)), other = lhs;
  else if (GET_CODE (lhs) == AND
	   && CONST_INT_P (XEXP (lhs, 1))
	   && rtx_equal_for_field_assignment_p (XEXP (lhs, 0), dest))
    c1 = INTVAL (XEXP (lhs, 1)), other = rhs;
  /* The second SUBREG that might get in the way is a paradoxical
     SUBREG around the first operand of the AND.  We want to 
     pretend the operand is as wide as the destination here.   We
     do this by adjusting the MEM to wider mode for the sole
     purpose of the call to rtx_equal_for_field_assignment_p.   Also
     note this trick only works for MEMs.  */
  else if (GET_CODE (lhs) == AND
	   && paradoxical_subreg_p (XEXP (lhs, 0))
	   && MEM_P (SUBREG_REG (XEXP (lhs, 0)))
	   && CONST_INT_P (XEXP (lhs, 1))
	   && rtx_equal_for_field_assignment_p (SUBREG_REG (XEXP (lhs, 0)),
						dest, true))
    c1 = INTVAL (XEXP (lhs, 1)), other = rhs;
  else
    return x;

  pos = get_pos_from_mask ((~c1) & GET_MODE_MASK (mode), &len);
  if (pos < 0
      || pos + len > GET_MODE_PRECISION (mode)
      || GET_MODE_PRECISION (mode) > HOST_BITS_PER_WIDE_INT
      || (c1 & nonzero_bits (other, mode)) != 0)
    return x;

  assign = make_extraction (VOIDmode, dest, pos, NULL_RTX, len, 1, 1, 0);
  if (assign == 0)
    return x;

  /* The mode to use for the source is the mode of the assignment, or of
     what is inside a possible STRICT_LOW_PART.  */
  machine_mode new_mode = (GET_CODE (assign) == STRICT_LOW_PART
			   ? GET_MODE (XEXP (assign, 0)) : GET_MODE (assign));

  /* Shift OTHER right POS places and make it the source, restricting it
     to the proper length and mode.  */

  src = canon_reg_for_combine (simplify_shift_const (NULL_RTX, LSHIFTRT,
						     src_mode, other, pos),
			       dest);
  src = force_to_mode (src, new_mode,
		       len >= HOST_BITS_PER_WIDE_INT
		       ? HOST_WIDE_INT_M1U
		       : (HOST_WIDE_INT_1U << len) - 1,
		       0);

  /* If SRC is masked by an AND that does not make a difference in
     the value being stored, strip it.  */
  if (GET_CODE (assign) == ZERO_EXTRACT
      && CONST_INT_P (XEXP (assign, 1))
      && INTVAL (XEXP (assign, 1)) < HOST_BITS_PER_WIDE_INT
      && GET_CODE (src) == AND
      && CONST_INT_P (XEXP (src, 1))
      && UINTVAL (XEXP (src, 1))
	 == (HOST_WIDE_INT_1U << INTVAL (XEXP (assign, 1))) - 1)
    src = XEXP (src, 0);

  return gen_rtx_SET (assign, src);
}

/* See if X is of the form (+ (* a c) (* b c)) and convert to (* (+ a b) c)
   if so.  */

static rtx
apply_distributive_law (rtx x)
{
  enum rtx_code code = GET_CODE (x);
  enum rtx_code inner_code;
  rtx lhs, rhs, other;
  rtx tem;

  /* Distributivity is not true for floating point as it can change the
     value.  So we don't do it unless -funsafe-math-optimizations.  */
  if (FLOAT_MODE_P (GET_MODE (x))
      && ! flag_unsafe_math_optimizations)
    return x;

  /* The outer operation can only be one of the following:  */
  if (code != IOR && code != AND && code != XOR
      && code != PLUS && code != MINUS)
    return x;

  lhs = XEXP (x, 0);
  rhs = XEXP (x, 1);

  /* If either operand is a primitive we can't do anything, so get out
     fast.  */
  if (OBJECT_P (lhs) || OBJECT_P (rhs))
    return x;

  lhs = expand_compound_operation (lhs);
  rhs = expand_compound_operation (rhs);
  inner_code = GET_CODE (lhs);
  if (inner_code != GET_CODE (rhs))
    return x;

  /* See if the inner and outer operations distribute.  */
  switch (inner_code)
    {
    case LSHIFTRT:
    case ASHIFTRT:
    case AND:
    case IOR:
      /* These all distribute except over PLUS.  */
      if (code == PLUS || code == MINUS)
	return x;
      break;

    case MULT:
      if (code != PLUS && code != MINUS)
	return x;
      break;

    case ASHIFT:
      /* This is also a multiply, so it distributes over everything.  */
      break;

    /* This used to handle SUBREG, but this turned out to be counter-
       productive, since (subreg (op ...)) usually is not handled by
       insn patterns, and this "optimization" therefore transformed
       recognizable patterns into unrecognizable ones.  Therefore the
       SUBREG case was removed from here.

       It is possible that distributing SUBREG over arithmetic operations
       leads to an intermediate result than can then be optimized further,
       e.g. by moving the outer SUBREG to the other side of a SET as done
       in simplify_set.  This seems to have been the original intent of
       handling SUBREGs here.

       However, with current GCC this does not appear to actually happen,
       at least on major platforms.  If some case is found where removing
       the SUBREG case here prevents follow-on optimizations, distributing
       SUBREGs ought to be re-added at that place, e.g. in simplify_set.  */

    default:
      return x;
    }

  /* Set LHS and RHS to the inner operands (A and B in the example
     above) and set OTHER to the common operand (C in the example).
     There is only one way to do this unless the inner operation is
     commutative.  */
  if (COMMUTATIVE_ARITH_P (lhs)
      && rtx_equal_p (XEXP (lhs, 0), XEXP (rhs, 0)))
    other = XEXP (lhs, 0), lhs = XEXP (lhs, 1), rhs = XEXP (rhs, 1);
  else if (COMMUTATIVE_ARITH_P (lhs)
	   && rtx_equal_p (XEXP (lhs, 0), XEXP (rhs, 1)))
    other = XEXP (lhs, 0), lhs = XEXP (lhs, 1), rhs = XEXP (rhs, 0);
  else if (COMMUTATIVE_ARITH_P (lhs)
	   && rtx_equal_p (XEXP (lhs, 1), XEXP (rhs, 0)))
    other = XEXP (lhs, 1), lhs = XEXP (lhs, 0), rhs = XEXP (rhs, 1);
  else if (rtx_equal_p (XEXP (lhs, 1), XEXP (rhs, 1)))
    other = XEXP (lhs, 1), lhs = XEXP (lhs, 0), rhs = XEXP (rhs, 0);
  else
    return x;

  /* Form the new inner operation, seeing if it simplifies first.  */
  tem = simplify_gen_binary (code, GET_MODE (x), lhs, rhs);

  /* There is one exception to the general way of distributing:
     (a | c) ^ (b | c) -> (a ^ b) & ~c  */
  if (code == XOR && inner_code == IOR)
    {
      inner_code = AND;
      other = simplify_gen_unary (NOT, GET_MODE (x), other, GET_MODE (x));
    }

  /* We may be able to continuing distributing the result, so call
     ourselves recursively on the inner operation before forming the
     outer operation, which we return.  */
  return simplify_gen_binary (inner_code, GET_MODE (x),
			      apply_distributive_law (tem), other);
}

/* See if X is of the form (* (+ A B) C), and if so convert to
   (+ (* A C) (* B C)) and try to simplify.

   Most of the time, this results in no change.  However, if some of
   the operands are the same or inverses of each other, simplifications
   will result.

   For example, (and (ior A B) (not B)) can occur as the result of
   expanding a bit field assignment.  When we apply the distributive
   law to this, we get (ior (and (A (not B))) (and (B (not B)))),
   which then simplifies to (and (A (not B))).

   Note that no checks happen on the validity of applying the inverse
   distributive law.  This is pointless since we can do it in the
   few places where this routine is called.

   N is the index of the term that is decomposed (the arithmetic operation,
   i.e. (+ A B) in the first example above).  !N is the index of the term that
   is distributed, i.e. of C in the first example above.  */
static rtx
distribute_and_simplify_rtx (rtx x, int n)
{
  machine_mode mode;
  enum rtx_code outer_code, inner_code;
  rtx decomposed, distributed, inner_op0, inner_op1, new_op0, new_op1, tmp;

  /* Distributivity is not true for floating point as it can change the
     value.  So we don't do it unless -funsafe-math-optimizations.  */
  if (FLOAT_MODE_P (GET_MODE (x))
      && ! flag_unsafe_math_optimizations)
    return NULL_RTX;

  decomposed = XEXP (x, n);
  if (!ARITHMETIC_P (decomposed))
    return NULL_RTX;

  mode = GET_MODE (x);
  outer_code = GET_CODE (x);
  distributed = XEXP (x, !n);

  inner_code = GET_CODE (decomposed);
  inner_op0 = XEXP (decomposed, 0);
  inner_op1 = XEXP (decomposed, 1);

  /* Special case (and (xor B C) (not A)), which is equivalent to
     (xor (ior A B) (ior A C))  */
  if (outer_code == AND && inner_code == XOR && GET_CODE (distributed) == NOT)
    {
      distributed = XEXP (distributed, 0);
      outer_code = IOR;
    }

  if (n == 0)
    {
      /* Distribute the second term.  */
      new_op0 = simplify_gen_binary (outer_code, mode, inner_op0, distributed);
      new_op1 = simplify_gen_binary (outer_code, mode, inner_op1, distributed);
    }
  else
    {
      /* Distribute the first term.  */
      new_op0 = simplify_gen_binary (outer_code, mode, distributed, inner_op0);
      new_op1 = simplify_gen_binary (outer_code, mode, distributed, inner_op1);
    }

  tmp = apply_distributive_law (simplify_gen_binary (inner_code, mode,
						     new_op0, new_op1));
  if (GET_CODE (tmp) != outer_code
      && (set_src_cost (tmp, mode, optimize_this_for_speed_p)
	  < set_src_cost (x, mode, optimize_this_for_speed_p)))
    return tmp;

  return NULL_RTX;
}

/* Simplify a logical `and' of VAROP with the constant CONSTOP, to be done
   in MODE.  Return an equivalent form, if different from (and VAROP
   (const_int CONSTOP)).  Otherwise, return NULL_RTX.  */

static rtx
simplify_and_const_int_1 (scalar_int_mode mode, rtx varop,
			  unsigned HOST_WIDE_INT constop)
{
  unsigned HOST_WIDE_INT nonzero;
  unsigned HOST_WIDE_INT orig_constop;
  rtx orig_varop;
  int i;

  orig_varop = varop;
  orig_constop = constop;
  if (GET_CODE (varop) == CLOBBER)
    return NULL_RTX;

  /* Simplify VAROP knowing that we will be only looking at some of the
     bits in it.

     Note by passing in CONSTOP, we guarantee that the bits not set in
     CONSTOP are not significant and will never be examined.  We must
     ensure that is the case by explicitly masking out those bits
     before returning.  */
  varop = force_to_mode (varop, mode, constop, 0);

  /* If VAROP is a CLOBBER, we will fail so return it.  */
  if (GET_CODE (varop) == CLOBBER)
    return varop;

  /* If VAROP is a CONST_INT, then we need to apply the mask in CONSTOP
     to VAROP and return the new constant.  */
  if (CONST_INT_P (varop))
    return gen_int_mode (INTVAL (varop) & constop, mode);

  /* See what bits may be nonzero in VAROP.  Unlike the general case of
     a call to nonzero_bits, here we don't care about bits outside
     MODE.  */

  nonzero = nonzero_bits (varop, mode) & GET_MODE_MASK (mode);

  /* Turn off all bits in the constant that are known to already be zero.
     Thus, if the AND isn't needed at all, we will have CONSTOP == NONZERO_BITS
     which is tested below.  */

  constop &= nonzero;

  /* If we don't have any bits left, return zero.  */
  if (constop == 0)
    return const0_rtx;

  /* If VAROP is a NEG of something known to be zero or 1 and CONSTOP is
     a power of two, we can replace this with an ASHIFT.  */
  if (GET_CODE (varop) == NEG && nonzero_bits (XEXP (varop, 0), mode) == 1
      && (i = exact_log2 (constop)) >= 0)
    return simplify_shift_const (NULL_RTX, ASHIFT, mode, XEXP (varop, 0), i);

  /* If VAROP is an IOR or XOR, apply the AND to both branches of the IOR
     or XOR, then try to apply the distributive law.  This may eliminate
     operations if either branch can be simplified because of the AND.
     It may also make some cases more complex, but those cases probably
     won't match a pattern either with or without this.  */

  if (GET_CODE (varop) == IOR || GET_CODE (varop) == XOR)
    {
      scalar_int_mode varop_mode = as_a <scalar_int_mode> (GET_MODE (varop));
      return
	gen_lowpart
	  (mode,
	   apply_distributive_law
	   (simplify_gen_binary (GET_CODE (varop), varop_mode,
				 simplify_and_const_int (NULL_RTX, varop_mode,
							 XEXP (varop, 0),
							 constop),
				 simplify_and_const_int (NULL_RTX, varop_mode,
							 XEXP (varop, 1),
							 constop))));
    }

  /* If VAROP is PLUS, and the constant is a mask of low bits, distribute
     the AND and see if one of the operands simplifies to zero.  If so, we
     may eliminate it.  */

  if (GET_CODE (varop) == PLUS
      && pow2p_hwi (constop + 1))
    {
      rtx o0, o1;

      o0 = simplify_and_const_int (NULL_RTX, mode, XEXP (varop, 0), constop);
      o1 = simplify_and_const_int (NULL_RTX, mode, XEXP (varop, 1), constop);
      if (o0 == const0_rtx)
	return o1;
      if (o1 == const0_rtx)
	return o0;
    }

  /* Make a SUBREG if necessary.  If we can't make it, fail.  */
  varop = gen_lowpart (mode, varop);
  if (varop == NULL_RTX || GET_CODE (varop) == CLOBBER)
    return NULL_RTX;

  /* If we are only masking insignificant bits, return VAROP.  */
  if (constop == nonzero)
    return varop;

  if (varop == orig_varop && constop == orig_constop)
    return NULL_RTX;

  /* Otherwise, return an AND.  */
  return simplify_gen_binary (AND, mode, varop, gen_int_mode (constop, mode));
}


/* We have X, a logical `and' of VAROP with the constant CONSTOP, to be done
   in MODE.

   Return an equivalent form, if different from X.  Otherwise, return X.  If
   X is zero, we are to always construct the equivalent form.  */

static rtx
simplify_and_const_int (rtx x, scalar_int_mode mode, rtx varop,
			unsigned HOST_WIDE_INT constop)
{
  rtx tem = simplify_and_const_int_1 (mode, varop, constop);
  if (tem)
    return tem;

  if (!x)
    x = simplify_gen_binary (AND, GET_MODE (varop), varop,
			     gen_int_mode (constop, mode));
  if (GET_MODE (x) != mode)
    x = gen_lowpart (mode, x);
  return x;
}

/* Given a REG X of mode XMODE, compute which bits in X can be nonzero.
   We don't care about bits outside of those defined in MODE.

   For most X this is simply GET_MODE_MASK (GET_MODE (MODE)), but if X is
   a shift, AND, or zero_extract, we can do better.  */

static rtx
reg_nonzero_bits_for_combine (const_rtx x, scalar_int_mode xmode,
			      scalar_int_mode mode,
			      unsigned HOST_WIDE_INT *nonzero)
{
  rtx tem;
  reg_stat_type *rsp;

  /* If X is a register whose nonzero bits value is current, use it.
     Otherwise, if X is a register whose value we can find, use that
     value.  Otherwise, use the previously-computed global nonzero bits
     for this register.  */

  rsp = &reg_stat[REGNO (x)];
  if (rsp->last_set_value != 0
      && (rsp->last_set_mode == mode
	  || (REGNO (x) >= FIRST_PSEUDO_REGISTER
	      && GET_MODE_CLASS (rsp->last_set_mode) == MODE_INT
	      && GET_MODE_CLASS (mode) == MODE_INT))
      && ((rsp->last_set_label >= label_tick_ebb_start
	   && rsp->last_set_label < label_tick)
	  || (rsp->last_set_label == label_tick
              && DF_INSN_LUID (rsp->last_set) < subst_low_luid)
	  || (REGNO (x) >= FIRST_PSEUDO_REGISTER
	      && REGNO (x) < reg_n_sets_max
	      && REG_N_SETS (REGNO (x)) == 1
	      && !REGNO_REG_SET_P
		  (DF_LR_IN (ENTRY_BLOCK_PTR_FOR_FN (cfun)->next_bb),
		   REGNO (x)))))
    {
      /* Note that, even if the precision of last_set_mode is lower than that
	 of mode, record_value_for_reg invoked nonzero_bits on the register
	 with nonzero_bits_mode (because last_set_mode is necessarily integral
	 and HWI_COMPUTABLE_MODE_P in this case) so bits in nonzero_bits_mode
	 are all valid, hence in mode too since nonzero_bits_mode is defined
	 to the largest HWI_COMPUTABLE_MODE_P mode.  */
      *nonzero &= rsp->last_set_nonzero_bits;
      return NULL;
    }

  tem = get_last_value (x);
  if (tem)
    {
      if (SHORT_IMMEDIATES_SIGN_EXTEND)
	tem = sign_extend_short_imm (tem, xmode, GET_MODE_PRECISION (mode));

      return tem;
    }

  if (nonzero_sign_valid && rsp->nonzero_bits)
    {
      unsigned HOST_WIDE_INT mask = rsp->nonzero_bits;

      if (GET_MODE_PRECISION (xmode) < GET_MODE_PRECISION (mode))
	/* We don't know anything about the upper bits.  */
	mask |= GET_MODE_MASK (mode) ^ GET_MODE_MASK (xmode);

      *nonzero &= mask;
    }

  return NULL;
}

/* Given a reg X of mode XMODE, return the number of bits at the high-order
   end of X that are known to be equal to the sign bit.  X will be used
   in mode MODE; the returned value will always be between 1 and the
   number of bits in MODE.  */

static rtx
reg_num_sign_bit_copies_for_combine (const_rtx x, scalar_int_mode xmode,
				     scalar_int_mode mode,
				     unsigned int *result)
{
  rtx tem;
  reg_stat_type *rsp;

  rsp = &reg_stat[REGNO (x)];
  if (rsp->last_set_value != 0
      && rsp->last_set_mode == mode
      && ((rsp->last_set_label >= label_tick_ebb_start
	   && rsp->last_set_label < label_tick)
	  || (rsp->last_set_label == label_tick
              && DF_INSN_LUID (rsp->last_set) < subst_low_luid)
	  || (REGNO (x) >= FIRST_PSEUDO_REGISTER
	      && REGNO (x) < reg_n_sets_max
	      && REG_N_SETS (REGNO (x)) == 1
	      && !REGNO_REG_SET_P
		  (DF_LR_IN (ENTRY_BLOCK_PTR_FOR_FN (cfun)->next_bb),
		   REGNO (x)))))
    {
      *result = rsp->last_set_sign_bit_copies;
      return NULL;
    }

  tem = get_last_value (x);
  if (tem != 0)
    return tem;

  if (nonzero_sign_valid && rsp->sign_bit_copies != 0
      && GET_MODE_PRECISION (xmode) == GET_MODE_PRECISION (mode))
    *result = rsp->sign_bit_copies;

  return NULL;
}

/* Return the number of "extended" bits there are in X, when interpreted
   as a quantity in MODE whose signedness is indicated by UNSIGNEDP.  For
   unsigned quantities, this is the number of high-order zero bits.
   For signed quantities, this is the number of copies of the sign bit
   minus 1.  In both case, this function returns the number of "spare"
   bits.  For example, if two quantities for which this function returns
   at least 1 are added, the addition is known not to overflow.

   This function will always return 0 unless called during combine, which
   implies that it must be called from a define_split.  */

unsigned int
extended_count (const_rtx x, machine_mode mode, int unsignedp)
{
  if (nonzero_sign_valid == 0)
    return 0;

  scalar_int_mode int_mode;
  return (unsignedp
	  ? (is_a <scalar_int_mode> (mode, &int_mode)
	     && HWI_COMPUTABLE_MODE_P (int_mode)
	     ? (unsigned int) (GET_MODE_PRECISION (int_mode) - 1
			       - floor_log2 (nonzero_bits (x, int_mode)))
	     : 0)
	  : num_sign_bit_copies (x, mode) - 1);
}

/* This function is called from `simplify_shift_const' to merge two
   outer operations.  Specifically, we have already found that we need
   to perform operation *POP0 with constant *PCONST0 at the outermost
   position.  We would now like to also perform OP1 with constant CONST1
   (with *POP0 being done last).

   Return 1 if we can do the operation and update *POP0 and *PCONST0 with
   the resulting operation.  *PCOMP_P is set to 1 if we would need to
   complement the innermost operand, otherwise it is unchanged.

   MODE is the mode in which the operation will be done.  No bits outside
   the width of this mode matter.  It is assumed that the width of this mode
   is smaller than or equal to HOST_BITS_PER_WIDE_INT.

   If *POP0 or OP1 are UNKNOWN, it means no operation is required.  Only NEG, PLUS,
   IOR, XOR, and AND are supported.  We may set *POP0 to SET if the proper
   result is simply *PCONST0.

   If the resulting operation cannot be expressed as one operation, we
   return 0 and do not change *POP0, *PCONST0, and *PCOMP_P.  */

static int
merge_outer_ops (enum rtx_code *pop0, HOST_WIDE_INT *pconst0, enum rtx_code op1, HOST_WIDE_INT const1, machine_mode mode, int *pcomp_p)
{
  enum rtx_code op0 = *pop0;
  HOST_WIDE_INT const0 = *pconst0;

  const0 &= GET_MODE_MASK (mode);
  const1 &= GET_MODE_MASK (mode);

  /* If OP0 is an AND, clear unimportant bits in CONST1.  */
  if (op0 == AND)
    const1 &= const0;

  /* If OP0 or OP1 is UNKNOWN, this is easy.  Similarly if they are the same or
     if OP0 is SET.  */

  if (op1 == UNKNOWN || op0 == SET)
    return 1;

  else if (op0 == UNKNOWN)
    op0 = op1, const0 = const1;

  else if (op0 == op1)
    {
      switch (op0)
	{
	case AND:
	  const0 &= const1;
	  break;
	case IOR:
	  const0 |= const1;
	  break;
	case XOR:
	  const0 ^= const1;
	  break;
	case PLUS:
	  const0 += const1;
	  break;
	case NEG:
	  op0 = UNKNOWN;
	  break;
	default:
	  break;
	}
    }

  /* Otherwise, if either is a PLUS or NEG, we can't do anything.  */
  else if (op0 == PLUS || op1 == PLUS || op0 == NEG || op1 == NEG)
    return 0;

  /* If the two constants aren't the same, we can't do anything.  The
     remaining six cases can all be done.  */
  else if (const0 != const1)
    return 0;

  else
    switch (op0)
      {
      case IOR:
	if (op1 == AND)
	  /* (a & b) | b == b */
	  op0 = SET;
	else /* op1 == XOR */
	  /* (a ^ b) | b == a | b */
	  {;}
	break;

      case XOR:
	if (op1 == AND)
	  /* (a & b) ^ b == (~a) & b */
	  op0 = AND, *pcomp_p = 1;
	else /* op1 == IOR */
	  /* (a | b) ^ b == a & ~b */
	  op0 = AND, const0 = ~const0;
	break;

      case AND:
	if (op1 == IOR)
	  /* (a | b) & b == b */
	op0 = SET;
	else /* op1 == XOR */
	  /* (a ^ b) & b) == (~a) & b */
	  *pcomp_p = 1;
	break;
      default:
	break;
      }

  /* Check for NO-OP cases.  */
  const0 &= GET_MODE_MASK (mode);
  if (const0 == 0
      && (op0 == IOR || op0 == XOR || op0 == PLUS))
    op0 = UNKNOWN;
  else if (const0 == 0 && op0 == AND)
    op0 = SET;
  else if ((unsigned HOST_WIDE_INT) const0 == GET_MODE_MASK (mode)
	   && op0 == AND)
    op0 = UNKNOWN;

  *pop0 = op0;

  /* ??? Slightly redundant with the above mask, but not entirely.
     Moving this above means we'd have to sign-extend the mode mask
     for the final test.  */
  if (op0 != UNKNOWN && op0 != NEG)
    *pconst0 = trunc_int_for_mode (const0, mode);

  return 1;
}

/* A helper to simplify_shift_const_1 to determine the mode we can perform
   the shift in.  The original shift operation CODE is performed on OP in
   ORIG_MODE.  Return the wider mode MODE if we can perform the operation
   in that mode.  Return ORIG_MODE otherwise.  We can also assume that the
   result of the shift is subject to operation OUTER_CODE with operand
   OUTER_CONST.  */

static scalar_int_mode
try_widen_shift_mode (enum rtx_code code, rtx op, int count,
		      scalar_int_mode orig_mode, scalar_int_mode mode,
		      enum rtx_code outer_code, HOST_WIDE_INT outer_const)
{
  gcc_assert (GET_MODE_PRECISION (mode) > GET_MODE_PRECISION (orig_mode));

  /* In general we can't perform in wider mode for right shift and rotate.  */
  switch (code)
    {
    case ASHIFTRT:
      /* We can still widen if the bits brought in from the left are identical
	 to the sign bit of ORIG_MODE.  */
      if (num_sign_bit_copies (op, mode)
	  > (unsigned) (GET_MODE_PRECISION (mode)
			- GET_MODE_PRECISION (orig_mode)))
	return mode;
      return orig_mode;

    case LSHIFTRT:
      /* Similarly here but with zero bits.  */
      if (HWI_COMPUTABLE_MODE_P (mode)
	  && (nonzero_bits (op, mode) & ~GET_MODE_MASK (orig_mode)) == 0)
	return mode;

      /* We can also widen if the bits brought in will be masked off.  This
	 operation is performed in ORIG_MODE.  */
      if (outer_code == AND)
	{
	  int care_bits = low_bitmask_len (orig_mode, outer_const);

	  if (care_bits >= 0
	      && GET_MODE_PRECISION (orig_mode) - care_bits >= count)
	    return mode;
	}
      /* fall through */

    case ROTATE:
      return orig_mode;

    case ROTATERT:
      gcc_unreachable ();

    default:
      return mode;
    }
}

/* Simplify a shift of VAROP by ORIG_COUNT bits.  CODE says what kind
   of shift.  The result of the shift is RESULT_MODE.  Return NULL_RTX
   if we cannot simplify it.  Otherwise, return a simplified value.

   The shift is normally computed in the widest mode we find in VAROP, as
   long as it isn't a different number of words than RESULT_MODE.  Exceptions
   are ASHIFTRT and ROTATE, which are always done in their original mode.  */

static rtx
simplify_shift_const_1 (enum rtx_code code, machine_mode result_mode,
			rtx varop, int orig_count)
{
  enum rtx_code orig_code = code;
  rtx orig_varop = varop;
  int count, log2;
  machine_mode mode = result_mode;
  machine_mode shift_mode;
  scalar_int_mode tmode, inner_mode, int_mode, int_varop_mode, int_result_mode;
  /* We form (outer_op (code varop count) (outer_const)).  */
  enum rtx_code outer_op = UNKNOWN;
  HOST_WIDE_INT outer_const = 0;
  int complement_p = 0;
  rtx new_rtx, x;

  /* Make sure and truncate the "natural" shift on the way in.  We don't
     want to do this inside the loop as it makes it more difficult to
     combine shifts.  */
  if (SHIFT_COUNT_TRUNCATED)
    orig_count &= GET_MODE_UNIT_BITSIZE (mode) - 1;

  /* If we were given an invalid count, don't do anything except exactly
     what was requested.  */

  if (orig_count < 0 || orig_count >= (int) GET_MODE_UNIT_PRECISION (mode))
    return NULL_RTX;

  count = orig_count;

  /* Unless one of the branches of the `if' in this loop does a `continue',
     we will `break' the loop after the `if'.  */

  while (count != 0)
    {
      /* If we have an operand of (clobber (const_int 0)), fail.  */
      if (GET_CODE (varop) == CLOBBER)
	return NULL_RTX;

      /* Convert ROTATERT to ROTATE.  */
      if (code == ROTATERT)
	{
	  unsigned int bitsize = GET_MODE_UNIT_PRECISION (result_mode);
	  code = ROTATE;
	  count = bitsize - count;
	}

      shift_mode = result_mode;
      if (shift_mode != mode)
	{
	  /* We only change the modes of scalar shifts.  */
	  int_mode = as_a <scalar_int_mode> (mode);
	  int_result_mode = as_a <scalar_int_mode> (result_mode);
	  shift_mode = try_widen_shift_mode (code, varop, count,
					     int_result_mode, int_mode,
					     outer_op, outer_const);
	}

      scalar_int_mode shift_unit_mode
	= as_a <scalar_int_mode> (GET_MODE_INNER (shift_mode));

      /* Handle cases where the count is greater than the size of the mode
	 minus 1.  For ASHIFT, use the size minus one as the count (this can
	 occur when simplifying (lshiftrt (ashiftrt ..))).  For rotates,
	 take the count modulo the size.  For other shifts, the result is
	 zero.

	 Since these shifts are being produced by the compiler by combining
	 multiple operations, each of which are defined, we know what the
	 result is supposed to be.  */

      if (count > (GET_MODE_PRECISION (shift_unit_mode) - 1))
	{
	  if (code == ASHIFTRT)
	    count = GET_MODE_PRECISION (shift_unit_mode) - 1;
	  else if (code == ROTATE || code == ROTATERT)
	    count %= GET_MODE_PRECISION (shift_unit_mode);
	  else
	    {
	      /* We can't simply return zero because there may be an
		 outer op.  */
	      varop = const0_rtx;
	      count = 0;
	      break;
	    }
	}

      /* If we discovered we had to complement VAROP, leave.  Making a NOT
	 here would cause an infinite loop.  */
      if (complement_p)
	break;

      if (shift_mode == shift_unit_mode)
	{
	  /* An arithmetic right shift of a quantity known to be -1 or 0
	     is a no-op.  */
	  if (code == ASHIFTRT
	      && (num_sign_bit_copies (varop, shift_unit_mode)
		  == GET_MODE_PRECISION (shift_unit_mode)))
	    {
	      count = 0;
	      break;
	    }

	  /* If we are doing an arithmetic right shift and discarding all but
	     the sign bit copies, this is equivalent to doing a shift by the
	     bitsize minus one.  Convert it into that shift because it will
	     often allow other simplifications.  */

	  if (code == ASHIFTRT
	      && (count + num_sign_bit_copies (varop, shift_unit_mode)
		  >= GET_MODE_PRECISION (shift_unit_mode)))
	    count = GET_MODE_PRECISION (shift_unit_mode) - 1;

	  /* We simplify the tests below and elsewhere by converting
	     ASHIFTRT to LSHIFTRT if we know the sign bit is clear.
	     `make_compound_operation' will convert it to an ASHIFTRT for
	     those machines (such as VAX) that don't have an LSHIFTRT.  */
	  if (code == ASHIFTRT
	      && HWI_COMPUTABLE_MODE_P (shift_unit_mode)
	      && val_signbit_known_clear_p (shift_unit_mode,
					    nonzero_bits (varop,
							  shift_unit_mode)))
	    code = LSHIFTRT;

	  if (((code == LSHIFTRT
		&& HWI_COMPUTABLE_MODE_P (shift_unit_mode)
		&& !(nonzero_bits (varop, shift_unit_mode) >> count))
	       || (code == ASHIFT
		   && HWI_COMPUTABLE_MODE_P (shift_unit_mode)
		   && !((nonzero_bits (varop, shift_unit_mode) << count)
			& GET_MODE_MASK (shift_unit_mode))))
	      && !side_effects_p (varop))
	    varop = const0_rtx;
	}

      switch (GET_CODE (varop))
	{
	case SIGN_EXTEND:
	case ZERO_EXTEND:
	case SIGN_EXTRACT:
	case ZERO_EXTRACT:
	  new_rtx = expand_compound_operation (varop);
	  if (new_rtx != varop)
	    {
	      varop = new_rtx;
	      continue;
	    }
	  break;

	case MEM:
	  /* The following rules apply only to scalars.  */
	  if (shift_mode != shift_unit_mode)
	    break;
	  int_mode = as_a <scalar_int_mode> (mode);

	  /* If we have (xshiftrt (mem ...) C) and C is MODE_WIDTH
	     minus the width of a smaller mode, we can do this with a
	     SIGN_EXTEND or ZERO_EXTEND from the narrower memory location.  */
	  if ((code == ASHIFTRT || code == LSHIFTRT)
	      && ! mode_dependent_address_p (XEXP (varop, 0),
					     MEM_ADDR_SPACE (varop))
	      && ! MEM_VOLATILE_P (varop)
	      && (int_mode_for_size (GET_MODE_BITSIZE (int_mode) - count, 1)
		  .exists (&tmode)))
	    {
	      new_rtx = adjust_address_nv (varop, tmode,
					   BYTES_BIG_ENDIAN ? 0
					   : count / BITS_PER_UNIT);

	      varop = gen_rtx_fmt_e (code == ASHIFTRT ? SIGN_EXTEND
				     : ZERO_EXTEND, int_mode, new_rtx);
	      count = 0;
	      continue;
	    }
	  break;

	case SUBREG:
	  /* The following rules apply only to scalars.  */
	  if (shift_mode != shift_unit_mode)
	    break;
	  int_mode = as_a <scalar_int_mode> (mode);
	  int_varop_mode = as_a <scalar_int_mode> (GET_MODE (varop));

	  /* If VAROP is a SUBREG, strip it as long as the inner operand has
	     the same number of words as what we've seen so far.  Then store
	     the widest mode in MODE.  */
	  if (subreg_lowpart_p (varop)
	      && is_int_mode (GET_MODE (SUBREG_REG (varop)), &inner_mode)
	      && GET_MODE_SIZE (inner_mode) > GET_MODE_SIZE (int_varop_mode)
	      && (CEIL (GET_MODE_SIZE (inner_mode), UNITS_PER_WORD)
		  == CEIL (GET_MODE_SIZE (int_mode), UNITS_PER_WORD))
	      && GET_MODE_CLASS (int_varop_mode) == MODE_INT)
	    {
	      varop = SUBREG_REG (varop);
	      if (GET_MODE_SIZE (inner_mode) > GET_MODE_SIZE (int_mode))
		mode = inner_mode;
	      continue;
	    }
	  break;

	case MULT:
	  /* Some machines use MULT instead of ASHIFT because MULT
	     is cheaper.  But it is still better on those machines to
	     merge two shifts into one.  */
	  if (CONST_INT_P (XEXP (varop, 1))
	      && (log2 = exact_log2 (UINTVAL (XEXP (varop, 1)))) >= 0)
	    {
	      rtx log2_rtx = gen_int_shift_amount (GET_MODE (varop), log2);
	      varop = simplify_gen_binary (ASHIFT, GET_MODE (varop),
					   XEXP (varop, 0), log2_rtx);
	      continue;
	    }
	  break;

	case UDIV:
	  /* Similar, for when divides are cheaper.  */
	  if (CONST_INT_P (XEXP (varop, 1))
	      && (log2 = exact_log2 (UINTVAL (XEXP (varop, 1)))) >= 0)
	    {
	      rtx log2_rtx = gen_int_shift_amount (GET_MODE (varop), log2);
	      varop = simplify_gen_binary (LSHIFTRT, GET_MODE (varop),
					   XEXP (varop, 0), log2_rtx);
	      continue;
	    }
	  break;

	case ASHIFTRT:
	  /* If we are extracting just the sign bit of an arithmetic
	     right shift, that shift is not needed.  However, the sign
	     bit of a wider mode may be different from what would be
	     interpreted as the sign bit in a narrower mode, so, if
	     the result is narrower, don't discard the shift.  */
	  if (code == LSHIFTRT
	      && count == (GET_MODE_UNIT_BITSIZE (result_mode) - 1)
	      && (GET_MODE_UNIT_BITSIZE (result_mode)
		  >= GET_MODE_UNIT_BITSIZE (GET_MODE (varop))))
	    {
	      varop = XEXP (varop, 0);
	      continue;
	    }

	  /* fall through */

	case LSHIFTRT:
	case ASHIFT:
	case ROTATE:
	  /* The following rules apply only to scalars.  */
	  if (shift_mode != shift_unit_mode)
	    break;
	  int_mode = as_a <scalar_int_mode> (mode);
	  int_varop_mode = as_a <scalar_int_mode> (GET_MODE (varop));
	  int_result_mode = as_a <scalar_int_mode> (result_mode);

	  /* Here we have two nested shifts.  The result is usually the
	     AND of a new shift with a mask.  We compute the result below.  */
	  if (CONST_INT_P (XEXP (varop, 1))
	      && INTVAL (XEXP (varop, 1)) >= 0
	      && INTVAL (XEXP (varop, 1)) < GET_MODE_PRECISION (int_varop_mode)
	      && HWI_COMPUTABLE_MODE_P (int_result_mode)
	      && HWI_COMPUTABLE_MODE_P (int_mode))
	    {
	      enum rtx_code first_code = GET_CODE (varop);
	      unsigned int first_count = INTVAL (XEXP (varop, 1));
	      unsigned HOST_WIDE_INT mask;
	      rtx mask_rtx;

	      /* We have one common special case.  We can't do any merging if
		 the inner code is an ASHIFTRT of a smaller mode.  However, if
		 we have (ashift:M1 (subreg:M1 (ashiftrt:M2 FOO C1) 0) C2)
		 with C2 == GET_MODE_BITSIZE (M1) - GET_MODE_BITSIZE (M2),
		 we can convert it to
		 (ashiftrt:M1 (ashift:M1 (and:M1 (subreg:M1 FOO 0) C3) C2) C1).
		 This simplifies certain SIGN_EXTEND operations.  */
	      if (code == ASHIFT && first_code == ASHIFTRT
		  && count == (GET_MODE_PRECISION (int_result_mode)
			       - GET_MODE_PRECISION (int_varop_mode)))
		{
		  /* C3 has the low-order C1 bits zero.  */

		  mask = GET_MODE_MASK (int_mode)
			 & ~((HOST_WIDE_INT_1U << first_count) - 1);

		  varop = simplify_and_const_int (NULL_RTX, int_result_mode,
						  XEXP (varop, 0), mask);
		  varop = simplify_shift_const (NULL_RTX, ASHIFT,
						int_result_mode, varop, count);
		  count = first_count;
		  code = ASHIFTRT;
		  continue;
		}

	      /* If this was (ashiftrt (ashift foo C1) C2) and FOO has more
		 than C1 high-order bits equal to the sign bit, we can convert
		 this to either an ASHIFT or an ASHIFTRT depending on the
		 two counts.

		 We cannot do this if VAROP's mode is not SHIFT_UNIT_MODE.  */

	      if (code == ASHIFTRT && first_code == ASHIFT
		  && int_varop_mode == shift_unit_mode
		  && (num_sign_bit_copies (XEXP (varop, 0), shift_unit_mode)
		      > first_count))
		{
		  varop = XEXP (varop, 0);
		  count -= first_count;
		  if (count < 0)
		    {
		      count = -count;
		      code = ASHIFT;
		    }

		  continue;
		}

	      /* There are some cases we can't do.  If CODE is ASHIFTRT,
		 we can only do this if FIRST_CODE is also ASHIFTRT.

		 We can't do the case when CODE is ROTATE and FIRST_CODE is
		 ASHIFTRT.

		 If the mode of this shift is not the mode of the outer shift,
		 we can't do this if either shift is a right shift or ROTATE.

		 Finally, we can't do any of these if the mode is too wide
		 unless the codes are the same.

		 Handle the case where the shift codes are the same
		 first.  */

	      if (code == first_code)
		{
		  if (int_varop_mode != int_result_mode
		      && (code == ASHIFTRT || code == LSHIFTRT
			  || code == ROTATE))
		    break;

		  count += first_count;
		  varop = XEXP (varop, 0);
		  continue;
		}

	      if (code == ASHIFTRT
		  || (code == ROTATE && first_code == ASHIFTRT)
		  || GET_MODE_PRECISION (int_mode) > HOST_BITS_PER_WIDE_INT
		  || (int_varop_mode != int_result_mode
		      && (first_code == ASHIFTRT || first_code == LSHIFTRT
			  || first_code == ROTATE
			  || code == ROTATE)))
		break;

	      /* To compute the mask to apply after the shift, shift the
		 nonzero bits of the inner shift the same way the
		 outer shift will.  */

	      mask_rtx = gen_int_mode (nonzero_bits (varop, int_varop_mode),
				       int_result_mode);
	      rtx count_rtx = gen_int_shift_amount (int_result_mode, count);
	      mask_rtx
		= simplify_const_binary_operation (code, int_result_mode,
						   mask_rtx, count_rtx);

	      /* Give up if we can't compute an outer operation to use.  */
	      if (mask_rtx == 0
		  || !CONST_INT_P (mask_rtx)
		  || ! merge_outer_ops (&outer_op, &outer_const, AND,
					INTVAL (mask_rtx),
					int_result_mode, &complement_p))
		break;

	      /* If the shifts are in the same direction, we add the
		 counts.  Otherwise, we subtract them.  */
	      if ((code == ASHIFTRT || code == LSHIFTRT)
		  == (first_code == ASHIFTRT || first_code == LSHIFTRT))
		count += first_count;
	      else
		count -= first_count;

	      /* If COUNT is positive, the new shift is usually CODE,
		 except for the two exceptions below, in which case it is
		 FIRST_CODE.  If the count is negative, FIRST_CODE should
		 always be used  */
	      if (count > 0
		  && ((first_code == ROTATE && code == ASHIFT)
		      || (first_code == ASHIFTRT && code == LSHIFTRT)))
		code = first_code;
	      else if (count < 0)
		code = first_code, count = -count;

	      varop = XEXP (varop, 0);
	      continue;
	    }

	  /* If we have (A << B << C) for any shift, we can convert this to
	     (A << C << B).  This wins if A is a constant.  Only try this if
	     B is not a constant.  */

	  else if (GET_CODE (varop) == code
		   && CONST_INT_P (XEXP (varop, 0))
		   && !CONST_INT_P (XEXP (varop, 1)))
	    {
	      /* For ((unsigned) (cstULL >> count)) >> cst2 we have to make
		 sure the result will be masked.  See PR70222.  */
	      if (code == LSHIFTRT
		  && int_mode != int_result_mode
		  && !merge_outer_ops (&outer_op, &outer_const, AND,
				       GET_MODE_MASK (int_result_mode)
				       >> orig_count, int_result_mode,
				       &complement_p))
		break;
	      /* For ((int) (cstLL >> count)) >> cst2 just give up.  Queuing
		 up outer sign extension (often left and right shift) is
		 hardly more efficient than the original.  See PR70429.  */
	      if (code == ASHIFTRT && int_mode != int_result_mode)
		break;

	      rtx count_rtx = gen_int_shift_amount (int_result_mode, count);
	      rtx new_rtx = simplify_const_binary_operation (code, int_mode,
							     XEXP (varop, 0),
							     count_rtx);
	      varop = gen_rtx_fmt_ee (code, int_mode, new_rtx, XEXP (varop, 1));
	      count = 0;
	      continue;
	    }
	  break;

	case NOT:
	  /* The following rules apply only to scalars.  */
	  if (shift_mode != shift_unit_mode)
	    break;

	  /* Make this fit the case below.  */
	  varop = gen_rtx_XOR (mode, XEXP (varop, 0), constm1_rtx);
	  continue;

	case IOR:
	case AND:
	case XOR:
	  /* The following rules apply only to scalars.  */
	  if (shift_mode != shift_unit_mode)
	    break;
	  int_varop_mode = as_a <scalar_int_mode> (GET_MODE (varop));
	  int_result_mode = as_a <scalar_int_mode> (result_mode);

	  /* If we have (xshiftrt (ior (plus X (const_int -1)) X) C)
	     with C the size of VAROP - 1 and the shift is logical if
	     STORE_FLAG_VALUE is 1 and arithmetic if STORE_FLAG_VALUE is -1,
	     we have an (le X 0) operation.   If we have an arithmetic shift
	     and STORE_FLAG_VALUE is 1 or we have a logical shift with
	     STORE_FLAG_VALUE of -1, we have a (neg (le X 0)) operation.  */

	  if (GET_CODE (varop) == IOR && GET_CODE (XEXP (varop, 0)) == PLUS
	      && XEXP (XEXP (varop, 0), 1) == constm1_rtx
	      && (STORE_FLAG_VALUE == 1 || STORE_FLAG_VALUE == -1)
	      && (code == LSHIFTRT || code == ASHIFTRT)
	      && count == (GET_MODE_PRECISION (int_varop_mode) - 1)
	      && rtx_equal_p (XEXP (XEXP (varop, 0), 0), XEXP (varop, 1)))
	    {
	      count = 0;
	      varop = gen_rtx_LE (int_varop_mode, XEXP (varop, 1),
				  const0_rtx);

	      if (STORE_FLAG_VALUE == 1 ? code == ASHIFTRT : code == LSHIFTRT)
		varop = gen_rtx_NEG (int_varop_mode, varop);

	      continue;
	    }

	  /* If we have (shift (logical)), move the logical to the outside
	     to allow it to possibly combine with another logical and the
	     shift to combine with another shift.  This also canonicalizes to
	     what a ZERO_EXTRACT looks like.  Also, some machines have
	     (and (shift)) insns.  */

	  if (CONST_INT_P (XEXP (varop, 1))
	      /* We can't do this if we have (ashiftrt (xor))  and the
		 constant has its sign bit set in shift_unit_mode with
		 shift_unit_mode wider than result_mode.  */
	      && !(code == ASHIFTRT && GET_CODE (varop) == XOR
		   && int_result_mode != shift_unit_mode
		   && trunc_int_for_mode (INTVAL (XEXP (varop, 1)),
					  shift_unit_mode) < 0)
	      && (new_rtx = simplify_const_binary_operation
		  (code, int_result_mode,
		   gen_int_mode (INTVAL (XEXP (varop, 1)), int_result_mode),
		   gen_int_shift_amount (int_result_mode, count))) != 0
	      && CONST_INT_P (new_rtx)
	      && merge_outer_ops (&outer_op, &outer_const, GET_CODE (varop),
				  INTVAL (new_rtx), int_result_mode,
				  &complement_p))
	    {
	      varop = XEXP (varop, 0);
	      continue;
	    }

	  /* If we can't do that, try to simplify the shift in each arm of the
	     logical expression, make a new logical expression, and apply
	     the inverse distributive law.  This also can't be done for
	     (ashiftrt (xor)) where we've widened the shift and the constant
	     changes the sign bit.  */
	  if (CONST_INT_P (XEXP (varop, 1))
	      && !(code == ASHIFTRT && GET_CODE (varop) == XOR
		   && int_result_mode != shift_unit_mode
		   && trunc_int_for_mode (INTVAL (XEXP (varop, 1)),
					  shift_unit_mode) < 0))
	    {
	      rtx lhs = simplify_shift_const (NULL_RTX, code, shift_unit_mode,
					      XEXP (varop, 0), count);
	      rtx rhs = simplify_shift_const (NULL_RTX, code, shift_unit_mode,
					      XEXP (varop, 1), count);

	      varop = simplify_gen_binary (GET_CODE (varop), shift_unit_mode,
					   lhs, rhs);
	      varop = apply_distributive_law (varop);

	      count = 0;
	      continue;
	    }
	  break;

	case EQ:
	  /* The following rules apply only to scalars.  */
	  if (shift_mode != shift_unit_mode)
	    break;
	  int_result_mode = as_a <scalar_int_mode> (result_mode);

	  /* Convert (lshiftrt (eq FOO 0) C) to (xor FOO 1) if STORE_FLAG_VALUE
	     says that the sign bit can be tested, FOO has mode MODE, C is
	     GET_MODE_PRECISION (MODE) - 1, and FOO has only its low-order bit
	     that may be nonzero.  */
	  if (code == LSHIFTRT
	      && XEXP (varop, 1) == const0_rtx
	      && GET_MODE (XEXP (varop, 0)) == int_result_mode
	      && count == (GET_MODE_PRECISION (int_result_mode) - 1)
	      && HWI_COMPUTABLE_MODE_P (int_result_mode)
	      && STORE_FLAG_VALUE == -1
	      && nonzero_bits (XEXP (varop, 0), int_result_mode) == 1
	      && merge_outer_ops (&outer_op, &outer_const, XOR, 1,
				  int_result_mode, &complement_p))
	    {
	      varop = XEXP (varop, 0);
	      count = 0;
	      continue;
	    }
	  break;

	case NEG:
	  /* The following rules apply only to scalars.  */
	  if (shift_mode != shift_unit_mode)
	    break;
	  int_result_mode = as_a <scalar_int_mode> (result_mode);

	  /* (lshiftrt (neg A) C) where A is either 0 or 1 and C is one less
	     than the number of bits in the mode is equivalent to A.  */
	  if (code == LSHIFTRT
	      && count == (GET_MODE_PRECISION (int_result_mode) - 1)
	      && nonzero_bits (XEXP (varop, 0), int_result_mode) == 1)
	    {
	      varop = XEXP (varop, 0);
	      count = 0;
	      continue;
	    }

	  /* NEG commutes with ASHIFT since it is multiplication.  Move the
	     NEG outside to allow shifts to combine.  */
	  if (code == ASHIFT
	      && merge_outer_ops (&outer_op, &outer_const, NEG, 0,
				  int_result_mode, &complement_p))
	    {
	      varop = XEXP (varop, 0);
	      continue;
	    }
	  break;

	case PLUS:
	  /* The following rules apply only to scalars.  */
	  if (shift_mode != shift_unit_mode)
	    break;
	  int_result_mode = as_a <scalar_int_mode> (result_mode);

	  /* (lshiftrt (plus A -1) C) where A is either 0 or 1 and C
	     is one less than the number of bits in the mode is
	     equivalent to (xor A 1).  */
	  if (code == LSHIFTRT
	      && count == (GET_MODE_PRECISION (int_result_mode) - 1)
	      && XEXP (varop, 1) == constm1_rtx
	      && nonzero_bits (XEXP (varop, 0), int_result_mode) == 1
	      && merge_outer_ops (&outer_op, &outer_const, XOR, 1,
				  int_result_mode, &complement_p))
	    {
	      count = 0;
	      varop = XEXP (varop, 0);
	      continue;
	    }

	  /* If we have (xshiftrt (plus FOO BAR) C), and the only bits
	     that might be nonzero in BAR are those being shifted out and those
	     bits are known zero in FOO, we can replace the PLUS with FOO.
	     Similarly in the other operand order.  This code occurs when
	     we are computing the size of a variable-size array.  */

	  if ((code == ASHIFTRT || code == LSHIFTRT)
	      && count < HOST_BITS_PER_WIDE_INT
	      && nonzero_bits (XEXP (varop, 1), int_result_mode) >> count == 0
	      && (nonzero_bits (XEXP (varop, 1), int_result_mode)
		  & nonzero_bits (XEXP (varop, 0), int_result_mode)) == 0)
	    {
	      varop = XEXP (varop, 0);
	      continue;
	    }
	  else if ((code == ASHIFTRT || code == LSHIFTRT)
		   && count < HOST_BITS_PER_WIDE_INT
		   && HWI_COMPUTABLE_MODE_P (int_result_mode)
		   && (nonzero_bits (XEXP (varop, 0), int_result_mode)
		       >> count) == 0
		   && (nonzero_bits (XEXP (varop, 0), int_result_mode)
		       & nonzero_bits (XEXP (varop, 1), int_result_mode)) == 0)
	    {
	      varop = XEXP (varop, 1);
	      continue;
	    }

	  /* (ashift (plus foo C) N) is (plus (ashift foo N) C').  */
	  if (code == ASHIFT
	      && CONST_INT_P (XEXP (varop, 1))
	      && (new_rtx = simplify_const_binary_operation
		  (ASHIFT, int_result_mode,
		   gen_int_mode (INTVAL (XEXP (varop, 1)), int_result_mode),
		   gen_int_shift_amount (int_result_mode, count))) != 0
	      && CONST_INT_P (new_rtx)
	      && merge_outer_ops (&outer_op, &outer_const, PLUS,
				  INTVAL (new_rtx), int_result_mode,
				  &complement_p))
	    {
	      varop = XEXP (varop, 0);
	      continue;
	    }

	  /* Check for 'PLUS signbit', which is the canonical form of 'XOR
	     signbit', and attempt to change the PLUS to an XOR and move it to
	     the outer operation as is done above in the AND/IOR/XOR case
	     leg for shift(logical). See details in logical handling above
	     for reasoning in doing so.  */
	  if (code == LSHIFTRT
	      && CONST_INT_P (XEXP (varop, 1))
	      && mode_signbit_p (int_result_mode, XEXP (varop, 1))
	      && (new_rtx = simplify_const_binary_operation
		  (code, int_result_mode,
		   gen_int_mode (INTVAL (XEXP (varop, 1)), int_result_mode),
		   gen_int_shift_amount (int_result_mode, count))) != 0
	      && CONST_INT_P (new_rtx)
	      && merge_outer_ops (&outer_op, &outer_const, XOR,
				  INTVAL (new_rtx), int_result_mode,
				  &complement_p))
	    {
	      varop = XEXP (varop, 0);
	      continue;
	    }

	  break;

	case MINUS:
	  /* The following rules apply only to scalars.  */
	  if (shift_mode != shift_unit_mode)
	    break;
	  int_varop_mode = as_a <scalar_int_mode> (GET_MODE (varop));

	  /* If we have (xshiftrt (minus (ashiftrt X C)) X) C)
	     with C the size of VAROP - 1 and the shift is logical if
	     STORE_FLAG_VALUE is 1 and arithmetic if STORE_FLAG_VALUE is -1,
	     we have a (gt X 0) operation.  If the shift is arithmetic with
	     STORE_FLAG_VALUE of 1 or logical with STORE_FLAG_VALUE == -1,
	     we have a (neg (gt X 0)) operation.  */

	  if ((STORE_FLAG_VALUE == 1 || STORE_FLAG_VALUE == -1)
	      && GET_CODE (XEXP (varop, 0)) == ASHIFTRT
	      && count == (GET_MODE_PRECISION (int_varop_mode) - 1)
	      && (code == LSHIFTRT || code == ASHIFTRT)
	      && CONST_INT_P (XEXP (XEXP (varop, 0), 1))
	      && INTVAL (XEXP (XEXP (varop, 0), 1)) == count
	      && rtx_equal_p (XEXP (XEXP (varop, 0), 0), XEXP (varop, 1)))
	    {
	      count = 0;
	      varop = gen_rtx_GT (int_varop_mode, XEXP (varop, 1),
				  const0_rtx);

	      if (STORE_FLAG_VALUE == 1 ? code == ASHIFTRT : code == LSHIFTRT)
		varop = gen_rtx_NEG (int_varop_mode, varop);

	      continue;
	    }
	  break;

	case TRUNCATE:
	  /* Change (lshiftrt (truncate (lshiftrt))) to (truncate (lshiftrt))
	     if the truncate does not affect the value.  */
	  if (code == LSHIFTRT
	      && GET_CODE (XEXP (varop, 0)) == LSHIFTRT
	      && CONST_INT_P (XEXP (XEXP (varop, 0), 1))
	      && (INTVAL (XEXP (XEXP (varop, 0), 1))
		  >= (GET_MODE_UNIT_PRECISION (GET_MODE (XEXP (varop, 0)))
		      - GET_MODE_UNIT_PRECISION (GET_MODE (varop)))))
	    {
	      rtx varop_inner = XEXP (varop, 0);
	      int new_count = count + INTVAL (XEXP (varop_inner, 1));
	      rtx new_count_rtx = gen_int_shift_amount (GET_MODE (varop_inner),
							new_count);
	      varop_inner = gen_rtx_LSHIFTRT (GET_MODE (varop_inner),
					      XEXP (varop_inner, 0),
					      new_count_rtx);
	      varop = gen_rtx_TRUNCATE (GET_MODE (varop), varop_inner);
	      count = 0;
	      continue;
	    }
	  break;

	default:
	  break;
	}

      break;
    }

  shift_mode = result_mode;
  if (shift_mode != mode)
    {
      /* We only change the modes of scalar shifts.  */
      int_mode = as_a <scalar_int_mode> (mode);
      int_result_mode = as_a <scalar_int_mode> (result_mode);
      shift_mode = try_widen_shift_mode (code, varop, count, int_result_mode,
					 int_mode, outer_op, outer_const);
    }

  /* We have now finished analyzing the shift.  The result should be
     a shift of type CODE with SHIFT_MODE shifting VAROP COUNT places.  If
     OUTER_OP is non-UNKNOWN, it is an operation that needs to be applied
     to the result of the shift.  OUTER_CONST is the relevant constant,
     but we must turn off all bits turned off in the shift.  */

  if (outer_op == UNKNOWN
      && orig_code == code && orig_count == count
      && varop == orig_varop
      && shift_mode == GET_MODE (varop))
    return NULL_RTX;

  /* Make a SUBREG if necessary.  If we can't make it, fail.  */
  varop = gen_lowpart (shift_mode, varop);
  if (varop == NULL_RTX || GET_CODE (varop) == CLOBBER)
    return NULL_RTX;

  /* If we have an outer operation and we just made a shift, it is
     possible that we could have simplified the shift were it not
     for the outer operation.  So try to do the simplification
     recursively.  */

  if (outer_op != UNKNOWN)
    x = simplify_shift_const_1 (code, shift_mode, varop, count);
  else
    x = NULL_RTX;

  if (x == NULL_RTX)
    x = simplify_gen_binary (code, shift_mode, varop,
			     gen_int_shift_amount (shift_mode, count));

  /* If we were doing an LSHIFTRT in a wider mode than it was originally,
     turn off all the bits that the shift would have turned off.  */
  if (orig_code == LSHIFTRT && result_mode != shift_mode)
    /* We only change the modes of scalar shifts.  */
    x = simplify_and_const_int (NULL_RTX, as_a <scalar_int_mode> (shift_mode),
				x, GET_MODE_MASK (result_mode) >> orig_count);

  /* Do the remainder of the processing in RESULT_MODE.  */
  x = gen_lowpart_or_truncate (result_mode, x);

  /* If COMPLEMENT_P is set, we have to complement X before doing the outer
     operation.  */
  if (complement_p)
    x = simplify_gen_unary (NOT, result_mode, x, result_mode);

  if (outer_op != UNKNOWN)
    {
      int_result_mode = as_a <scalar_int_mode> (result_mode);

      if (GET_RTX_CLASS (outer_op) != RTX_UNARY
	  && GET_MODE_PRECISION (int_result_mode) < HOST_BITS_PER_WIDE_INT)
	outer_const = trunc_int_for_mode (outer_const, int_result_mode);

      if (outer_op == AND)
	x = simplify_and_const_int (NULL_RTX, int_result_mode, x, outer_const);
      else if (outer_op == SET)
	{
	  /* This means that we have determined that the result is
	     equivalent to a constant.  This should be rare.  */
	  if (!side_effects_p (x))
	    x = GEN_INT (outer_const);
	}
      else if (GET_RTX_CLASS (outer_op) == RTX_UNARY)
	x = simplify_gen_unary (outer_op, int_result_mode, x, int_result_mode);
      else
	x = simplify_gen_binary (outer_op, int_result_mode, x,
				 GEN_INT (outer_const));
    }

  return x;
}

/* Simplify a shift of VAROP by COUNT bits.  CODE says what kind of shift.
   The result of the shift is RESULT_MODE.  If we cannot simplify it,
   return X or, if it is NULL, synthesize the expression with
   simplify_gen_binary.  Otherwise, return a simplified value.

   The shift is normally computed in the widest mode we find in VAROP, as
   long as it isn't a different number of words than RESULT_MODE.  Exceptions
   are ASHIFTRT and ROTATE, which are always done in their original mode.  */

static rtx
simplify_shift_const (rtx x, enum rtx_code code, machine_mode result_mode,
		      rtx varop, int count)
{
  rtx tem = simplify_shift_const_1 (code, result_mode, varop, count);
  if (tem)
    return tem;

  if (!x)
    x = simplify_gen_binary (code, GET_MODE (varop), varop,
			     gen_int_shift_amount (GET_MODE (varop), count));
  if (GET_MODE (x) != result_mode)
    x = gen_lowpart (result_mode, x);
  return x;
}


/* A subroutine of recog_for_combine.  See there for arguments and
   return value.  */

static int
recog_for_combine_1 (rtx *pnewpat, rtx_insn *insn, rtx *pnotes)
{
  rtx pat = *pnewpat;
  rtx pat_without_clobbers;
  int insn_code_number;
  int num_clobbers_to_add = 0;
  int i;
  rtx notes = NULL_RTX;
  rtx old_notes, old_pat;
  int old_icode;

  /* If PAT is a PARALLEL, check to see if it contains the CLOBBER
     we use to indicate that something didn't match.  If we find such a
     thing, force rejection.  */
  if (GET_CODE (pat) == PARALLEL)
    for (i = XVECLEN (pat, 0) - 1; i >= 0; i--)
      if (GET_CODE (XVECEXP (pat, 0, i)) == CLOBBER
	  && XEXP (XVECEXP (pat, 0, i), 0) == const0_rtx)
	return -1;

  old_pat = PATTERN (insn);
  old_notes = REG_NOTES (insn);
  PATTERN (insn) = pat;
  REG_NOTES (insn) = NULL_RTX;

  insn_code_number = recog (pat, insn, &num_clobbers_to_add);
  if (dump_file && (dump_flags & TDF_DETAILS))
    {
      if (insn_code_number < 0)
	fputs ("Failed to match this instruction:\n", dump_file);
      else
	fputs ("Successfully matched this instruction:\n", dump_file);
      print_rtl_single (dump_file, pat);
    }

  /* If it isn't, there is the possibility that we previously had an insn
     that clobbered some register as a side effect, but the combined
     insn doesn't need to do that.  So try once more without the clobbers
     unless this represents an ASM insn.  */

  if (insn_code_number < 0 && ! check_asm_operands (pat)
      && GET_CODE (pat) == PARALLEL)
    {
      int pos;

      for (pos = 0, i = 0; i < XVECLEN (pat, 0); i++)
	if (GET_CODE (XVECEXP (pat, 0, i)) != CLOBBER)
	  {
	    if (i != pos)
	      SUBST (XVECEXP (pat, 0, pos), XVECEXP (pat, 0, i));
	    pos++;
	  }

      SUBST_INT (XVECLEN (pat, 0), pos);

      if (pos == 1)
	pat = XVECEXP (pat, 0, 0);

      PATTERN (insn) = pat;
      insn_code_number = recog (pat, insn, &num_clobbers_to_add);
      if (dump_file && (dump_flags & TDF_DETAILS))
	{
	  if (insn_code_number < 0)
	    fputs ("Failed to match this instruction:\n", dump_file);
	  else
	    fputs ("Successfully matched this instruction:\n", dump_file);
	  print_rtl_single (dump_file, pat);
	}
    }

  pat_without_clobbers = pat;

  PATTERN (insn) = old_pat;
  REG_NOTES (insn) = old_notes;

  /* Recognize all noop sets, these will be killed by followup pass.  */
  if (insn_code_number < 0 && GET_CODE (pat) == SET && set_noop_p (pat))
    insn_code_number = NOOP_MOVE_INSN_CODE, num_clobbers_to_add = 0;

  /* If we had any clobbers to add, make a new pattern than contains
     them.  Then check to make sure that all of them are dead.  */
  if (num_clobbers_to_add)
    {
      rtx newpat = gen_rtx_PARALLEL (VOIDmode,
				     rtvec_alloc (GET_CODE (pat) == PARALLEL
						  ? (XVECLEN (pat, 0)
						     + num_clobbers_to_add)
						  : num_clobbers_to_add + 1));

      if (GET_CODE (pat) == PARALLEL)
	for (i = 0; i < XVECLEN (pat, 0); i++)
	  XVECEXP (newpat, 0, i) = XVECEXP (pat, 0, i);
      else
	XVECEXP (newpat, 0, 0) = pat;

      add_clobbers (newpat, insn_code_number);

      for (i = XVECLEN (newpat, 0) - num_clobbers_to_add;
	   i < XVECLEN (newpat, 0); i++)
	{
	  if (REG_P (XEXP (XVECEXP (newpat, 0, i), 0))
	      && ! reg_dead_at_p (XEXP (XVECEXP (newpat, 0, i), 0), insn))
	    return -1;
	  if (GET_CODE (XEXP (XVECEXP (newpat, 0, i), 0)) != SCRATCH)
	    {
	      gcc_assert (REG_P (XEXP (XVECEXP (newpat, 0, i), 0)));
	      notes = alloc_reg_note (REG_UNUSED,
				      XEXP (XVECEXP (newpat, 0, i), 0), notes);
	    }
	}
      pat = newpat;
    }

  if (insn_code_number >= 0
      && insn_code_number != NOOP_MOVE_INSN_CODE)
    {
      old_pat = PATTERN (insn);
      old_notes = REG_NOTES (insn);
      old_icode = INSN_CODE (insn);
      PATTERN (insn) = pat;
      REG_NOTES (insn) = notes;
      INSN_CODE (insn) = insn_code_number;

      /* Allow targets to reject combined insn.  */
      if (!targetm.legitimate_combined_insn (insn))
	{
	  if (dump_file && (dump_flags & TDF_DETAILS))
	    fputs ("Instruction not appropriate for target.",
		   dump_file);

	  /* Callers expect recog_for_combine to strip
	     clobbers from the pattern on failure.  */
	  pat = pat_without_clobbers;
	  notes = NULL_RTX;

	  insn_code_number = -1;
	}

      PATTERN (insn) = old_pat;
      REG_NOTES (insn) = old_notes;
      INSN_CODE (insn) = old_icode;
    }

  *pnewpat = pat;
  *pnotes = notes;

  return insn_code_number;
}

/* Change every ZERO_EXTRACT and ZERO_EXTEND of a SUBREG that can be
   expressed as an AND and maybe an LSHIFTRT, to that formulation.
   Return whether anything was so changed.  */

static bool
change_zero_ext (rtx pat)
{
  bool changed = false;
  rtx *src = &SET_SRC (pat);

  subrtx_ptr_iterator::array_type array;
  FOR_EACH_SUBRTX_PTR (iter, array, src, NONCONST)
    {
      rtx x = **iter;
      scalar_int_mode mode, inner_mode;
      if (!is_a <scalar_int_mode> (GET_MODE (x), &mode))
	continue;
      int size;

      if (GET_CODE (x) == ZERO_EXTRACT
	  && CONST_INT_P (XEXP (x, 1))
	  && CONST_INT_P (XEXP (x, 2))
	  && is_a <scalar_int_mode> (GET_MODE (XEXP (x, 0)), &inner_mode)
	  && GET_MODE_PRECISION (inner_mode) <= GET_MODE_PRECISION (mode))
	{
	  size = INTVAL (XEXP (x, 1));

	  int start = INTVAL (XEXP (x, 2));
	  if (BITS_BIG_ENDIAN)
	    start = GET_MODE_PRECISION (inner_mode) - size - start;

	  if (start != 0)
	    x = gen_rtx_LSHIFTRT (inner_mode, XEXP (x, 0),
				  gen_int_shift_amount (inner_mode, start));
	  else
	    x = XEXP (x, 0);

	  if (mode != inner_mode)
	    {
	      if (REG_P (x) && HARD_REGISTER_P (x)
		  && !can_change_dest_mode (x, 0, mode))
		continue;

	      x = gen_lowpart_SUBREG (mode, x);
	    }
	}
      else if (GET_CODE (x) == ZERO_EXTEND
	       && GET_CODE (XEXP (x, 0)) == SUBREG
	       && SCALAR_INT_MODE_P (GET_MODE (SUBREG_REG (XEXP (x, 0))))
	       && !paradoxical_subreg_p (XEXP (x, 0))
	       && subreg_lowpart_p (XEXP (x, 0)))
	{
	  inner_mode = as_a <scalar_int_mode> (GET_MODE (XEXP (x, 0)));
	  size = GET_MODE_PRECISION (inner_mode);
	  x = SUBREG_REG (XEXP (x, 0));
	  if (GET_MODE (x) != mode)
	    {
	      if (REG_P (x) && HARD_REGISTER_P (x)
		  && !can_change_dest_mode (x, 0, mode))
		continue;

	      x = gen_lowpart_SUBREG (mode, x);
	    }
	}
      else if (GET_CODE (x) == ZERO_EXTEND
	       && REG_P (XEXP (x, 0))
	       && HARD_REGISTER_P (XEXP (x, 0))
	       && can_change_dest_mode (XEXP (x, 0), 0, mode))
	{
	  inner_mode = as_a <scalar_int_mode> (GET_MODE (XEXP (x, 0)));
	  size = GET_MODE_PRECISION (inner_mode);
	  x = gen_rtx_REG (mode, REGNO (XEXP (x, 0)));
	}
      else
	continue;

      if (!(GET_CODE (x) == LSHIFTRT
	    && CONST_INT_P (XEXP (x, 1))
	    && size + INTVAL (XEXP (x, 1)) == GET_MODE_PRECISION (mode)))
	{
	  wide_int mask = wi::mask (size, false, GET_MODE_PRECISION (mode));
	  x = gen_rtx_AND (mode, x, immed_wide_int_const (mask, mode));
	}

      SUBST (**iter, x);
      changed = true;
    }

  if (changed)
    FOR_EACH_SUBRTX_PTR (iter, array, src, NONCONST)
      maybe_swap_commutative_operands (**iter);

  rtx *dst = &SET_DEST (pat);
  scalar_int_mode mode;
  if (GET_CODE (*dst) == ZERO_EXTRACT
      && REG_P (XEXP (*dst, 0))
      && is_a <scalar_int_mode> (GET_MODE (XEXP (*dst, 0)), &mode)
      && CONST_INT_P (XEXP (*dst, 1))
      && CONST_INT_P (XEXP (*dst, 2)))
    {
      rtx reg = XEXP (*dst, 0);
      int width = INTVAL (XEXP (*dst, 1));
      int offset = INTVAL (XEXP (*dst, 2));
      int reg_width = GET_MODE_PRECISION (mode);
      if (BITS_BIG_ENDIAN)
	offset = reg_width - width - offset;

      rtx x, y, z, w;
      wide_int mask = wi::shifted_mask (offset, width, true, reg_width);
      wide_int mask2 = wi::shifted_mask (offset, width, false, reg_width);
      x = gen_rtx_AND (mode, reg, immed_wide_int_const (mask, mode));
      if (offset)
	y = gen_rtx_ASHIFT (mode, SET_SRC (pat), GEN_INT (offset));
      else
	y = SET_SRC (pat);
      z = gen_rtx_AND (mode, y, immed_wide_int_const (mask2, mode));
      w = gen_rtx_IOR (mode, x, z);
      SUBST (SET_DEST (pat), reg);
      SUBST (SET_SRC (pat), w);

      changed = true;
    }

  return changed;
}

/* Like recog, but we receive the address of a pointer to a new pattern.
   We try to match the rtx that the pointer points to.
   If that fails, we may try to modify or replace the pattern,
   storing the replacement into the same pointer object.

   Modifications include deletion or addition of CLOBBERs.  If the
   instruction will still not match, we change ZERO_EXTEND and ZERO_EXTRACT
   to the equivalent AND and perhaps LSHIFTRT patterns, and try with that
   (and undo if that fails).

   PNOTES is a pointer to a location where any REG_UNUSED notes added for
   the CLOBBERs are placed.

   The value is the final insn code from the pattern ultimately matched,
   or -1.  */

static int
recog_for_combine (rtx *pnewpat, rtx_insn *insn, rtx *pnotes)
{
  rtx pat = *pnewpat;
  int insn_code_number = recog_for_combine_1 (pnewpat, insn, pnotes);
  if (insn_code_number >= 0 || check_asm_operands (pat))
    return insn_code_number;

  void *marker = get_undo_marker ();
  bool changed = false;

  if (GET_CODE (pat) == SET)
    changed = change_zero_ext (pat);
  else if (GET_CODE (pat) == PARALLEL)
    {
      int i;
      for (i = 0; i < XVECLEN (pat, 0); i++)
	{
	  rtx set = XVECEXP (pat, 0, i);
	  if (GET_CODE (set) == SET)
	    changed |= change_zero_ext (set);
	}
    }

  if (changed)
    {
      insn_code_number = recog_for_combine_1 (pnewpat, insn, pnotes);

      if (insn_code_number < 0)
	undo_to_marker (marker);
    }

  return insn_code_number;
}

/* Like gen_lowpart_general but for use by combine.  In combine it
   is not possible to create any new pseudoregs.  However, it is
   safe to create invalid memory addresses, because combine will
   try to recognize them and all they will do is make the combine
   attempt fail.

   If for some reason this cannot do its job, an rtx
   (clobber (const_int 0)) is returned.
   An insn containing that will not be recognized.  */

static rtx
gen_lowpart_for_combine (machine_mode omode, rtx x)
{
  machine_mode imode = GET_MODE (x);
  rtx result;

  if (omode == imode)
    return x;

  /* We can only support MODE being wider than a word if X is a
     constant integer or has a mode the same size.  */
  if (maybe_gt (GET_MODE_SIZE (omode), UNITS_PER_WORD)
      && ! (CONST_SCALAR_INT_P (x)
	    || known_eq (GET_MODE_SIZE (imode), GET_MODE_SIZE (omode))))
    goto fail;

  /* X might be a paradoxical (subreg (mem)).  In that case, gen_lowpart
     won't know what to do.  So we will strip off the SUBREG here and
     process normally.  */
  if (GET_CODE (x) == SUBREG && MEM_P (SUBREG_REG (x)))
    {
      x = SUBREG_REG (x);

      /* For use in case we fall down into the address adjustments
	 further below, we need to adjust the known mode and size of
	 x; imode and isize, since we just adjusted x.  */
      imode = GET_MODE (x);

      if (imode == omode)
	return x;
    }

  result = gen_lowpart_common (omode, x);

  if (result)
    return result;

  if (MEM_P (x))
    {
      /* Refuse to work on a volatile memory ref or one with a mode-dependent
	 address.  */
      if (MEM_VOLATILE_P (x)
	  || mode_dependent_address_p (XEXP (x, 0), MEM_ADDR_SPACE (x)))
	goto fail;

      /* If we want to refer to something bigger than the original memref,
	 generate a paradoxical subreg instead.  That will force a reload
	 of the original memref X.  */
      if (paradoxical_subreg_p (omode, imode))
	return gen_rtx_SUBREG (omode, x, 0);

      poly_int64 offset = byte_lowpart_offset (omode, imode);
      return adjust_address_nv (x, omode, offset);
    }

  /* If X is a comparison operator, rewrite it in a new mode.  This
     probably won't match, but may allow further simplifications.  */
  else if (COMPARISON_P (x))
    return gen_rtx_fmt_ee (GET_CODE (x), omode, XEXP (x, 0), XEXP (x, 1));

  /* If we couldn't simplify X any other way, just enclose it in a
     SUBREG.  Normally, this SUBREG won't match, but some patterns may
     include an explicit SUBREG or we may simplify it further in combine.  */
  else
    {
      rtx res;

      if (imode == VOIDmode)
	{
	  imode = int_mode_for_mode (omode).require ();
	  x = gen_lowpart_common (imode, x);
	  if (x == NULL)
	    goto fail;
	}
      res = lowpart_subreg (omode, x, imode);
      if (res)
	return res;
    }

 fail:
  return gen_rtx_CLOBBER (omode, const0_rtx);
}

/* Try to simplify a comparison between OP0 and a constant OP1,
   where CODE is the comparison code that will be tested, into a
   (CODE OP0 const0_rtx) form.

   The result is a possibly different comparison code to use.
   *POP1 may be updated.  */

static enum rtx_code
simplify_compare_const (enum rtx_code code, machine_mode mode,
			rtx op0, rtx *pop1)
{
  scalar_int_mode int_mode;
  HOST_WIDE_INT const_op = INTVAL (*pop1);

  /* Get the constant we are comparing against and turn off all bits
     not on in our mode.  */
  if (mode != VOIDmode)
    const_op = trunc_int_for_mode (const_op, mode);

  /* If we are comparing against a constant power of two and the value
     being compared can only have that single bit nonzero (e.g., it was
     `and'ed with that bit), we can replace this with a comparison
     with zero.  */
  if (const_op
      && (code == EQ || code == NE || code == GE || code == GEU
	  || code == LT || code == LTU)
      && is_a <scalar_int_mode> (mode, &int_mode)
      && GET_MODE_PRECISION (int_mode) - 1 < HOST_BITS_PER_WIDE_INT
      && pow2p_hwi (const_op & GET_MODE_MASK (int_mode))
      && (nonzero_bits (op0, int_mode)
	  == (unsigned HOST_WIDE_INT) (const_op & GET_MODE_MASK (int_mode))))
    {
      code = (code == EQ || code == GE || code == GEU ? NE : EQ);
      const_op = 0;
    }

  /* Similarly, if we are comparing a value known to be either -1 or
     0 with -1, change it to the opposite comparison against zero.  */
  if (const_op == -1
      && (code == EQ || code == NE || code == GT || code == LE
	  || code == GEU || code == LTU)
      && is_a <scalar_int_mode> (mode, &int_mode)
      && num_sign_bit_copies (op0, int_mode) == GET_MODE_PRECISION (int_mode))
    {
      code = (code == EQ || code == LE || code == GEU ? NE : EQ);
      const_op = 0;
    }

  /* Do some canonicalizations based on the comparison code.  We prefer
     comparisons against zero and then prefer equality comparisons.
     If we can reduce the size of a constant, we will do that too.  */
  switch (code)
    {
    case LT:
      /* < C is equivalent to <= (C - 1) */
      if (const_op > 0)
	{
	  const_op -= 1;
	  code = LE;
	  /* ... fall through to LE case below.  */
	  gcc_fallthrough ();
	}
      else
	break;

    case LE:
      /* <= C is equivalent to < (C + 1); we do this for C < 0  */
      if (const_op < 0)
	{
	  const_op += 1;
	  code = LT;
	}

      /* If we are doing a <= 0 comparison on a value known to have
	 a zero sign bit, we can replace this with == 0.  */
      else if (const_op == 0
	       && is_a <scalar_int_mode> (mode, &int_mode)
	       && GET_MODE_PRECISION (int_mode) - 1 < HOST_BITS_PER_WIDE_INT
	       && (nonzero_bits (op0, int_mode)
		   & (HOST_WIDE_INT_1U << (GET_MODE_PRECISION (int_mode) - 1)))
	       == 0)
	code = EQ;
      break;

    case GE:
      /* >= C is equivalent to > (C - 1).  */
      if (const_op > 0)
	{
	  const_op -= 1;
	  code = GT;
	  /* ... fall through to GT below.  */
	  gcc_fallthrough ();
	}
      else
	break;

    case GT:
      /* > C is equivalent to >= (C + 1); we do this for C < 0.  */
      if (const_op < 0)
	{
	  const_op += 1;
	  code = GE;
	}

      /* If we are doing a > 0 comparison on a value known to have
	 a zero sign bit, we can replace this with != 0.  */
      else if (const_op == 0
	       && is_a <scalar_int_mode> (mode, &int_mode)
	       && GET_MODE_PRECISION (int_mode) - 1 < HOST_BITS_PER_WIDE_INT
	       && (nonzero_bits (op0, int_mode)
		   & (HOST_WIDE_INT_1U << (GET_MODE_PRECISION (int_mode) - 1)))
	       == 0)
	code = NE;
      break;

    case LTU:
      /* < C is equivalent to <= (C - 1).  */
      if (const_op > 0)
	{
	  const_op -= 1;
	  code = LEU;
	  /* ... fall through ...  */
	  gcc_fallthrough ();
	}
      /* (unsigned) < 0x80000000 is equivalent to >= 0.  */
      else if (is_a <scalar_int_mode> (mode, &int_mode)
	       && GET_MODE_PRECISION (int_mode) - 1 < HOST_BITS_PER_WIDE_INT
	       && ((unsigned HOST_WIDE_INT) const_op
		   == HOST_WIDE_INT_1U << (GET_MODE_PRECISION (int_mode) - 1)))
	{
	  const_op = 0;
	  code = GE;
	  break;
	}
      else
	break;

    case LEU:
      /* unsigned <= 0 is equivalent to == 0 */
      if (const_op == 0)
	code = EQ;
      /* (unsigned) <= 0x7fffffff is equivalent to >= 0.  */
      else if (is_a <scalar_int_mode> (mode, &int_mode)
	       && GET_MODE_PRECISION (int_mode) - 1 < HOST_BITS_PER_WIDE_INT
	       && ((unsigned HOST_WIDE_INT) const_op
		   == ((HOST_WIDE_INT_1U
			<< (GET_MODE_PRECISION (int_mode) - 1)) - 1)))
	{
	  const_op = 0;
	  code = GE;
	}
      break;

    case GEU:
      /* >= C is equivalent to > (C - 1).  */
      if (const_op > 1)
	{
	  const_op -= 1;
	  code = GTU;
	  /* ... fall through ...  */
	  gcc_fallthrough ();
	}

      /* (unsigned) >= 0x80000000 is equivalent to < 0.  */
      else if (is_a <scalar_int_mode> (mode, &int_mode)
	       && GET_MODE_PRECISION (int_mode) - 1 < HOST_BITS_PER_WIDE_INT
	       && ((unsigned HOST_WIDE_INT) const_op
		   == HOST_WIDE_INT_1U << (GET_MODE_PRECISION (int_mode) - 1)))
	{
	  const_op = 0;
	  code = LT;
	  break;
	}
      else
	break;

    case GTU:
      /* unsigned > 0 is equivalent to != 0 */
      if (const_op == 0)
	code = NE;
      /* (unsigned) > 0x7fffffff is equivalent to < 0.  */
      else if (is_a <scalar_int_mode> (mode, &int_mode)
	       && GET_MODE_PRECISION (int_mode) - 1 < HOST_BITS_PER_WIDE_INT
	       && ((unsigned HOST_WIDE_INT) const_op
		   == (HOST_WIDE_INT_1U
		       << (GET_MODE_PRECISION (int_mode) - 1)) - 1))
	{
	  const_op = 0;
	  code = LT;
	}
      break;

    default:
      break;
    }

  *pop1 = GEN_INT (const_op);
  return code;
}

/* Simplify a comparison between *POP0 and *POP1 where CODE is the
   comparison code that will be tested.

   The result is a possibly different comparison code to use.  *POP0 and
   *POP1 may be updated.

   It is possible that we might detect that a comparison is either always
   true or always false.  However, we do not perform general constant
   folding in combine, so this knowledge isn't useful.  Such tautologies
   should have been detected earlier.  Hence we ignore all such cases.  */

static enum rtx_code
simplify_comparison (enum rtx_code code, rtx *pop0, rtx *pop1)
{
  rtx op0 = *pop0;
  rtx op1 = *pop1;
  rtx tem, tem1;
  int i;
  scalar_int_mode mode, inner_mode, tmode;
  opt_scalar_int_mode tmode_iter;

  /* Try a few ways of applying the same transformation to both operands.  */
  while (1)
    {
      /* The test below this one won't handle SIGN_EXTENDs on these machines,
	 so check specially.  */
      if (!WORD_REGISTER_OPERATIONS
	  && code != GTU && code != GEU && code != LTU && code != LEU
	  && GET_CODE (op0) == ASHIFTRT && GET_CODE (op1) == ASHIFTRT
	  && GET_CODE (XEXP (op0, 0)) == ASHIFT
	  && GET_CODE (XEXP (op1, 0)) == ASHIFT
	  && GET_CODE (XEXP (XEXP (op0, 0), 0)) == SUBREG
	  && GET_CODE (XEXP (XEXP (op1, 0), 0)) == SUBREG
	  && is_a <scalar_int_mode> (GET_MODE (op0), &mode)
	  && (is_a <scalar_int_mode>
	      (GET_MODE (SUBREG_REG (XEXP (XEXP (op0, 0), 0))), &inner_mode))
	  && inner_mode == GET_MODE (SUBREG_REG (XEXP (XEXP (op1, 0), 0)))
	  && CONST_INT_P (XEXP (op0, 1))
	  && XEXP (op0, 1) == XEXP (op1, 1)
	  && XEXP (op0, 1) == XEXP (XEXP (op0, 0), 1)
	  && XEXP (op0, 1) == XEXP (XEXP (op1, 0), 1)
	  && (INTVAL (XEXP (op0, 1))
	      == (GET_MODE_PRECISION (mode)
		  - GET_MODE_PRECISION (inner_mode))))
	{
	  op0 = SUBREG_REG (XEXP (XEXP (op0, 0), 0));
	  op1 = SUBREG_REG (XEXP (XEXP (op1, 0), 0));
	}

      /* If both operands are the same constant shift, see if we can ignore the
	 shift.  We can if the shift is a rotate or if the bits shifted out of
	 this shift are known to be zero for both inputs and if the type of
	 comparison is compatible with the shift.  */
      if (GET_CODE (op0) == GET_CODE (op1)
	  && HWI_COMPUTABLE_MODE_P (GET_MODE (op0))
	  && ((GET_CODE (op0) == ROTATE && (code == NE || code == EQ))
	      || ((GET_CODE (op0) == LSHIFTRT || GET_CODE (op0) == ASHIFT)
		  && (code != GT && code != LT && code != GE && code != LE))
	      || (GET_CODE (op0) == ASHIFTRT
		  && (code != GTU && code != LTU
		      && code != GEU && code != LEU)))
	  && CONST_INT_P (XEXP (op0, 1))
	  && INTVAL (XEXP (op0, 1)) >= 0
	  && INTVAL (XEXP (op0, 1)) < HOST_BITS_PER_WIDE_INT
	  && XEXP (op0, 1) == XEXP (op1, 1))
	{
	  machine_mode mode = GET_MODE (op0);
	  unsigned HOST_WIDE_INT mask = GET_MODE_MASK (mode);
	  int shift_count = INTVAL (XEXP (op0, 1));

	  if (GET_CODE (op0) == LSHIFTRT || GET_CODE (op0) == ASHIFTRT)
	    mask &= (mask >> shift_count) << shift_count;
	  else if (GET_CODE (op0) == ASHIFT)
	    mask = (mask & (mask << shift_count)) >> shift_count;

	  if ((nonzero_bits (XEXP (op0, 0), mode) & ~mask) == 0
	      && (nonzero_bits (XEXP (op1, 0), mode) & ~mask) == 0)
	    op0 = XEXP (op0, 0), op1 = XEXP (op1, 0);
	  else
	    break;
	}

      /* If both operands are AND's of a paradoxical SUBREG by constant, the
	 SUBREGs are of the same mode, and, in both cases, the AND would
	 be redundant if the comparison was done in the narrower mode,
	 do the comparison in the narrower mode (e.g., we are AND'ing with 1
	 and the operand's possibly nonzero bits are 0xffffff01; in that case
	 if we only care about QImode, we don't need the AND).  This case
	 occurs if the output mode of an scc insn is not SImode and
	 STORE_FLAG_VALUE == 1 (e.g., the 386).

	 Similarly, check for a case where the AND's are ZERO_EXTEND
	 operations from some narrower mode even though a SUBREG is not
	 present.  */

      else if (GET_CODE (op0) == AND && GET_CODE (op1) == AND
	       && CONST_INT_P (XEXP (op0, 1))
	       && CONST_INT_P (XEXP (op1, 1)))
	{
	  rtx inner_op0 = XEXP (op0, 0);
	  rtx inner_op1 = XEXP (op1, 0);
	  HOST_WIDE_INT c0 = INTVAL (XEXP (op0, 1));
	  HOST_WIDE_INT c1 = INTVAL (XEXP (op1, 1));
	  int changed = 0;

	  if (paradoxical_subreg_p (inner_op0)
	      && GET_CODE (inner_op1) == SUBREG
	      && HWI_COMPUTABLE_MODE_P (GET_MODE (SUBREG_REG (inner_op0)))
	      && (GET_MODE (SUBREG_REG (inner_op0))
		  == GET_MODE (SUBREG_REG (inner_op1)))
	      && ((~c0) & nonzero_bits (SUBREG_REG (inner_op0),
					GET_MODE (SUBREG_REG (inner_op0)))) == 0
	      && ((~c1) & nonzero_bits (SUBREG_REG (inner_op1),
					GET_MODE (SUBREG_REG (inner_op1)))) == 0)
	    {
	      op0 = SUBREG_REG (inner_op0);
	      op1 = SUBREG_REG (inner_op1);

	      /* The resulting comparison is always unsigned since we masked
		 off the original sign bit.  */
	      code = unsigned_condition (code);

	      changed = 1;
	    }

	  else if (c0 == c1)
	    FOR_EACH_MODE_UNTIL (tmode,
				 as_a <scalar_int_mode> (GET_MODE (op0)))
	      if ((unsigned HOST_WIDE_INT) c0 == GET_MODE_MASK (tmode))
		{
		  op0 = gen_lowpart_or_truncate (tmode, inner_op0);
		  op1 = gen_lowpart_or_truncate (tmode, inner_op1);
		  code = unsigned_condition (code);
		  changed = 1;
		  break;
		}

	  if (! changed)
	    break;
	}

      /* If both operands are NOT, we can strip off the outer operation
	 and adjust the comparison code for swapped operands; similarly for
	 NEG, except that this must be an equality comparison.  */
      else if ((GET_CODE (op0) == NOT && GET_CODE (op1) == NOT)
	       || (GET_CODE (op0) == NEG && GET_CODE (op1) == NEG
		   && (code == EQ || code == NE)))
	op0 = XEXP (op0, 0), op1 = XEXP (op1, 0), code = swap_condition (code);

      else
	break;
    }

  /* If the first operand is a constant, swap the operands and adjust the
     comparison code appropriately, but don't do this if the second operand
     is already a constant integer.  */
  if (swap_commutative_operands_p (op0, op1))
    {
      std::swap (op0, op1);
      code = swap_condition (code);
    }

  /* We now enter a loop during which we will try to simplify the comparison.
     For the most part, we only are concerned with comparisons with zero,
     but some things may really be comparisons with zero but not start
     out looking that way.  */

  while (CONST_INT_P (op1))
    {
      machine_mode raw_mode = GET_MODE (op0);
      scalar_int_mode int_mode;
      int equality_comparison_p;
      int sign_bit_comparison_p;
      int unsigned_comparison_p;
      HOST_WIDE_INT const_op;

      /* We only want to handle integral modes.  This catches VOIDmode,
	 CCmode, and the floating-point modes.  An exception is that we
	 can handle VOIDmode if OP0 is a COMPARE or a comparison
	 operation.  */

      if (GET_MODE_CLASS (raw_mode) != MODE_INT
	  && ! (raw_mode == VOIDmode
		&& (GET_CODE (op0) == COMPARE || COMPARISON_P (op0))))
	break;

      /* Try to simplify the compare to constant, possibly changing the
	 comparison op, and/or changing op1 to zero.  */
      code = simplify_compare_const (code, raw_mode, op0, &op1);
      const_op = INTVAL (op1);

      /* Compute some predicates to simplify code below.  */

      equality_comparison_p = (code == EQ || code == NE);
      sign_bit_comparison_p = ((code == LT || code == GE) && const_op == 0);
      unsigned_comparison_p = (code == LTU || code == LEU || code == GTU
			       || code == GEU);

      /* If this is a sign bit comparison and we can do arithmetic in
	 MODE, say that we will only be needing the sign bit of OP0.  */
      if (sign_bit_comparison_p
	  && is_a <scalar_int_mode> (raw_mode, &int_mode)
	  && HWI_COMPUTABLE_MODE_P (int_mode))
	op0 = force_to_mode (op0, int_mode,
			     HOST_WIDE_INT_1U
			     << (GET_MODE_PRECISION (int_mode) - 1),
			     0);

      if (COMPARISON_P (op0))
	{
	  /* We can't do anything if OP0 is a condition code value, rather
	     than an actual data value.  */
	  if (const_op != 0
	      || CC0_P (XEXP (op0, 0))
	      || GET_MODE_CLASS (GET_MODE (XEXP (op0, 0))) == MODE_CC)
	    break;

	  /* Get the two operands being compared.  */
	  if (GET_CODE (XEXP (op0, 0)) == COMPARE)
	    tem = XEXP (XEXP (op0, 0), 0), tem1 = XEXP (XEXP (op0, 0), 1);
	  else
	    tem = XEXP (op0, 0), tem1 = XEXP (op0, 1);

	  /* Check for the cases where we simply want the result of the
	     earlier test or the opposite of that result.  */
	  if (code == NE || code == EQ
	      || (val_signbit_known_set_p (raw_mode, STORE_FLAG_VALUE)
		  && (code == LT || code == GE)))
	    {
	      enum rtx_code new_code;
	      if (code == LT || code == NE)
		new_code = GET_CODE (op0);
	      else
		new_code = reversed_comparison_code (op0, NULL);

	      if (new_code != UNKNOWN)
		{
		  code = new_code;
		  op0 = tem;
		  op1 = tem1;
		  continue;
		}
	    }
	  break;
	}

      if (raw_mode == VOIDmode)
	break;
      scalar_int_mode mode = as_a <scalar_int_mode> (raw_mode);

      /* Now try cases based on the opcode of OP0.  If none of the cases
	 does a "continue", we exit this loop immediately after the
	 switch.  */

      unsigned int mode_width = GET_MODE_PRECISION (mode);
      unsigned HOST_WIDE_INT mask = GET_MODE_MASK (mode);
      switch (GET_CODE (op0))
	{
	case ZERO_EXTRACT:
	  /* If we are extracting a single bit from a variable position in
	     a constant that has only a single bit set and are comparing it
	     with zero, we can convert this into an equality comparison
	     between the position and the location of the single bit.  */
	  /* Except we can't if SHIFT_COUNT_TRUNCATED is set, since we might
	     have already reduced the shift count modulo the word size.  */
	  if (!SHIFT_COUNT_TRUNCATED
	      && CONST_INT_P (XEXP (op0, 0))
	      && XEXP (op0, 1) == const1_rtx
	      && equality_comparison_p && const_op == 0
	      && (i = exact_log2 (UINTVAL (XEXP (op0, 0)))) >= 0)
	    {
	      if (BITS_BIG_ENDIAN)
		i = BITS_PER_WORD - 1 - i;

	      op0 = XEXP (op0, 2);
	      op1 = GEN_INT (i);
	      const_op = i;

	      /* Result is nonzero iff shift count is equal to I.  */
	      code = reverse_condition (code);
	      continue;
	    }

	  /* fall through */

	case SIGN_EXTRACT:
	  tem = expand_compound_operation (op0);
	  if (tem != op0)
	    {
	      op0 = tem;
	      continue;
	    }
	  break;

	case NOT:
	  /* If testing for equality, we can take the NOT of the constant.  */
	  if (equality_comparison_p
	      && (tem = simplify_unary_operation (NOT, mode, op1, mode)) != 0)
	    {
	      op0 = XEXP (op0, 0);
	      op1 = tem;
	      continue;
	    }

	  /* If just looking at the sign bit, reverse the sense of the
	     comparison.  */
	  if (sign_bit_comparison_p)
	    {
	      op0 = XEXP (op0, 0);
	      code = (code == GE ? LT : GE);
	      continue;
	    }
	  break;

	case NEG:
	  /* If testing for equality, we can take the NEG of the constant.  */
	  if (equality_comparison_p
	      && (tem = simplify_unary_operation (NEG, mode, op1, mode)) != 0)
	    {
	      op0 = XEXP (op0, 0);
	      op1 = tem;
	      continue;
	    }

	  /* The remaining cases only apply to comparisons with zero.  */
	  if (const_op != 0)
	    break;

	  /* When X is ABS or is known positive,
	     (neg X) is < 0 if and only if X != 0.  */

	  if (sign_bit_comparison_p
	      && (GET_CODE (XEXP (op0, 0)) == ABS
		  || (mode_width <= HOST_BITS_PER_WIDE_INT
		      && (nonzero_bits (XEXP (op0, 0), mode)
			  & (HOST_WIDE_INT_1U << (mode_width - 1)))
			 == 0)))
	    {
	      op0 = XEXP (op0, 0);
	      code = (code == LT ? NE : EQ);
	      continue;
	    }

	  /* If we have NEG of something whose two high-order bits are the
	     same, we know that "(-a) < 0" is equivalent to "a > 0".  */
	  if (num_sign_bit_copies (op0, mode) >= 2)
	    {
	      op0 = XEXP (op0, 0);
	      code = swap_condition (code);
	      continue;
	    }
	  break;

	case ROTATE:
	  /* If we are testing equality and our count is a constant, we
	     can perform the inverse operation on our RHS.  */
	  if (equality_comparison_p && CONST_INT_P (XEXP (op0, 1))
	      && (tem = simplify_binary_operation (ROTATERT, mode,
						   op1, XEXP (op0, 1))) != 0)
	    {
	      op0 = XEXP (op0, 0);
	      op1 = tem;
	      continue;
	    }

	  /* If we are doing a < 0 or >= 0 comparison, it means we are testing
	     a particular bit.  Convert it to an AND of a constant of that
	     bit.  This will be converted into a ZERO_EXTRACT.  */
	  if (const_op == 0 && sign_bit_comparison_p
	      && CONST_INT_P (XEXP (op0, 1))
	      && mode_width <= HOST_BITS_PER_WIDE_INT)
	    {
	      op0 = simplify_and_const_int (NULL_RTX, mode, XEXP (op0, 0),
					    (HOST_WIDE_INT_1U
					     << (mode_width - 1
						 - INTVAL (XEXP (op0, 1)))));
	      code = (code == LT ? NE : EQ);
	      continue;
	    }

	  /* Fall through.  */

	case ABS:
	  /* ABS is ignorable inside an equality comparison with zero.  */
	  if (const_op == 0 && equality_comparison_p)
	    {
	      op0 = XEXP (op0, 0);
	      continue;
	    }
	  break;

	case SIGN_EXTEND:
	  /* Can simplify (compare (zero/sign_extend FOO) CONST) to
	     (compare FOO CONST) if CONST fits in FOO's mode and we
	     are either testing inequality or have an unsigned
	     comparison with ZERO_EXTEND or a signed comparison with
	     SIGN_EXTEND.  But don't do it if we don't have a compare
	     insn of the given mode, since we'd have to revert it
	     later on, and then we wouldn't know whether to sign- or
	     zero-extend.  */
	  if (is_int_mode (GET_MODE (XEXP (op0, 0)), &mode)
	      && ! unsigned_comparison_p
	      && HWI_COMPUTABLE_MODE_P (mode)
	      && trunc_int_for_mode (const_op, mode) == const_op
	      && have_insn_for (COMPARE, mode))
	    {
	      op0 = XEXP (op0, 0);
	      continue;
	    }
	  break;

	case SUBREG:
	  /* Check for the case where we are comparing A - C1 with C2, that is

	       (subreg:MODE (plus (A) (-C1))) op (C2)

	     with C1 a constant, and try to lift the SUBREG, i.e. to do the
	     comparison in the wider mode.  One of the following two conditions
	     must be true in order for this to be valid:

	       1. The mode extension results in the same bit pattern being added
		  on both sides and the comparison is equality or unsigned.  As
		  C2 has been truncated to fit in MODE, the pattern can only be
		  all 0s or all 1s.

	       2. The mode extension results in the sign bit being copied on
		  each side.

	     The difficulty here is that we have predicates for A but not for
	     (A - C1) so we need to check that C1 is within proper bounds so
	     as to perturbate A as little as possible.  */

	  if (mode_width <= HOST_BITS_PER_WIDE_INT
	      && subreg_lowpart_p (op0)
	      && is_a <scalar_int_mode> (GET_MODE (SUBREG_REG (op0)),
					 &inner_mode)
	      && GET_MODE_PRECISION (inner_mode) > mode_width
	      && GET_CODE (SUBREG_REG (op0)) == PLUS
	      && CONST_INT_P (XEXP (SUBREG_REG (op0), 1)))
	    {
	      rtx a = XEXP (SUBREG_REG (op0), 0);
	      HOST_WIDE_INT c1 = -INTVAL (XEXP (SUBREG_REG (op0), 1));

	      if ((c1 > 0
		   && (unsigned HOST_WIDE_INT) c1
		       < HOST_WIDE_INT_1U << (mode_width - 1)
		   && (equality_comparison_p || unsigned_comparison_p)
		   /* (A - C1) zero-extends if it is positive and sign-extends
		      if it is negative, C2 both zero- and sign-extends.  */
		   && (((nonzero_bits (a, inner_mode)
			 & ~GET_MODE_MASK (mode)) == 0
			&& const_op >= 0)
		       /* (A - C1) sign-extends if it is positive and 1-extends
			  if it is negative, C2 both sign- and 1-extends.  */
		       || (num_sign_bit_copies (a, inner_mode)
			   > (unsigned int) (GET_MODE_PRECISION (inner_mode)
					     - mode_width)
			   && const_op < 0)))
		  || ((unsigned HOST_WIDE_INT) c1
		       < HOST_WIDE_INT_1U << (mode_width - 2)
		      /* (A - C1) always sign-extends, like C2.  */
		      && num_sign_bit_copies (a, inner_mode)
			 > (unsigned int) (GET_MODE_PRECISION (inner_mode)
					   - (mode_width - 1))))
		{
		  op0 = SUBREG_REG (op0);
		  continue;
		}
	    }

	  /* If the inner mode is narrower and we are extracting the low part,
	     we can treat the SUBREG as if it were a ZERO_EXTEND.  */
	  if (paradoxical_subreg_p (op0))
	    ;
	  else if (subreg_lowpart_p (op0)
		   && GET_MODE_CLASS (mode) == MODE_INT
		   && is_int_mode (GET_MODE (SUBREG_REG (op0)), &inner_mode)
		   && (code == NE || code == EQ)
		   && GET_MODE_PRECISION (inner_mode) <= HOST_BITS_PER_WIDE_INT
		   && !paradoxical_subreg_p (op0)
		   && (nonzero_bits (SUBREG_REG (op0), inner_mode)
		       & ~GET_MODE_MASK (mode)) == 0)
	    {
	      /* Remove outer subregs that don't do anything.  */
	      tem = gen_lowpart (inner_mode, op1);

	      if ((nonzero_bits (tem, inner_mode)
		   & ~GET_MODE_MASK (mode)) == 0)
		{
		  op0 = SUBREG_REG (op0);
		  op1 = tem;
		  continue;
		}
	      break;
	    }
	  else
	    break;

	  /* FALLTHROUGH */

	case ZERO_EXTEND:
	  if (is_int_mode (GET_MODE (XEXP (op0, 0)), &mode)
	      && (unsigned_comparison_p || equality_comparison_p)
	      && HWI_COMPUTABLE_MODE_P (mode)
	      && (unsigned HOST_WIDE_INT) const_op <= GET_MODE_MASK (mode)
	      && const_op >= 0
	      && have_insn_for (COMPARE, mode))
	    {
	      op0 = XEXP (op0, 0);
	      continue;
	    }
	  break;

	case PLUS:
	  /* (eq (plus X A) B) -> (eq X (minus B A)).  We can only do
	     this for equality comparisons due to pathological cases involving
	     overflows.  */
	  if (equality_comparison_p
	      && (tem = simplify_binary_operation (MINUS, mode,
						   op1, XEXP (op0, 1))) != 0)
	    {
	      op0 = XEXP (op0, 0);
	      op1 = tem;
	      continue;
	    }

	  /* (plus (abs X) (const_int -1)) is < 0 if and only if X == 0.  */
	  if (const_op == 0 && XEXP (op0, 1) == constm1_rtx
	      && GET_CODE (XEXP (op0, 0)) == ABS && sign_bit_comparison_p)
	    {
	      op0 = XEXP (XEXP (op0, 0), 0);
	      code = (code == LT ? EQ : NE);
	      continue;
	    }
	  break;

	case MINUS:
	  /* We used to optimize signed comparisons against zero, but that
	     was incorrect.  Unsigned comparisons against zero (GTU, LEU)
	     arrive here as equality comparisons, or (GEU, LTU) are
	     optimized away.  No need to special-case them.  */

	  /* (eq (minus A B) C) -> (eq A (plus B C)) or
	     (eq B (minus A C)), whichever simplifies.  We can only do
	     this for equality comparisons due to pathological cases involving
	     overflows.  */
	  if (equality_comparison_p
	      && (tem = simplify_binary_operation (PLUS, mode,
						   XEXP (op0, 1), op1)) != 0)
	    {
	      op0 = XEXP (op0, 0);
	      op1 = tem;
	      continue;
	    }

	  if (equality_comparison_p
	      && (tem = simplify_binary_operation (MINUS, mode,
						   XEXP (op0, 0), op1)) != 0)
	    {
	      op0 = XEXP (op0, 1);
	      op1 = tem;
	      continue;
	    }

	  /* The sign bit of (minus (ashiftrt X C) X), where C is the number
	     of bits in X minus 1, is one iff X > 0.  */
	  if (sign_bit_comparison_p && GET_CODE (XEXP (op0, 0)) == ASHIFTRT
	      && CONST_INT_P (XEXP (XEXP (op0, 0), 1))
	      && UINTVAL (XEXP (XEXP (op0, 0), 1)) == mode_width - 1
	      && rtx_equal_p (XEXP (XEXP (op0, 0), 0), XEXP (op0, 1)))
	    {
	      op0 = XEXP (op0, 1);
	      code = (code == GE ? LE : GT);
	      continue;
	    }
	  break;

	case XOR:
	  /* (eq (xor A B) C) -> (eq A (xor B C)).  This is a simplification
	     if C is zero or B is a constant.  */
	  if (equality_comparison_p
	      && (tem = simplify_binary_operation (XOR, mode,
						   XEXP (op0, 1), op1)) != 0)
	    {
	      op0 = XEXP (op0, 0);
	      op1 = tem;
	      continue;
	    }
	  break;


	case IOR:
	  /* The sign bit of (ior (plus X (const_int -1)) X) is nonzero
	     iff X <= 0.  */
	  if (sign_bit_comparison_p && GET_CODE (XEXP (op0, 0)) == PLUS
	      && XEXP (XEXP (op0, 0), 1) == constm1_rtx
	      && rtx_equal_p (XEXP (XEXP (op0, 0), 0), XEXP (op0, 1)))
	    {
	      op0 = XEXP (op0, 1);
	      code = (code == GE ? GT : LE);
	      continue;
	    }
	  break;

	case AND:
	  /* Convert (and (xshift 1 X) Y) to (and (lshiftrt Y X) 1).  This
	     will be converted to a ZERO_EXTRACT later.  */
	  if (const_op == 0 && equality_comparison_p
	      && GET_CODE (XEXP (op0, 0)) == ASHIFT
	      && XEXP (XEXP (op0, 0), 0) == const1_rtx)
	    {
	      op0 = gen_rtx_LSHIFTRT (mode, XEXP (op0, 1),
				      XEXP (XEXP (op0, 0), 1));
	      op0 = simplify_and_const_int (NULL_RTX, mode, op0, 1);
	      continue;
	    }

	  /* If we are comparing (and (lshiftrt X C1) C2) for equality with
	     zero and X is a comparison and C1 and C2 describe only bits set
	     in STORE_FLAG_VALUE, we can compare with X.  */
	  if (const_op == 0 && equality_comparison_p
	      && mode_width <= HOST_BITS_PER_WIDE_INT
	      && CONST_INT_P (XEXP (op0, 1))
	      && GET_CODE (XEXP (op0, 0)) == LSHIFTRT
	      && CONST_INT_P (XEXP (XEXP (op0, 0), 1))
	      && INTVAL (XEXP (XEXP (op0, 0), 1)) >= 0
	      && INTVAL (XEXP (XEXP (op0, 0), 1)) < HOST_BITS_PER_WIDE_INT)
	    {
	      mask = ((INTVAL (XEXP (op0, 1)) & GET_MODE_MASK (mode))
		      << INTVAL (XEXP (XEXP (op0, 0), 1)));
	      if ((~STORE_FLAG_VALUE & mask) == 0
		  && (COMPARISON_P (XEXP (XEXP (op0, 0), 0))
		      || ((tem = get_last_value (XEXP (XEXP (op0, 0), 0))) != 0
			  && COMPARISON_P (tem))))
		{
		  op0 = XEXP (XEXP (op0, 0), 0);
		  continue;
		}
	    }

	  /* If we are doing an equality comparison of an AND of a bit equal
	     to the sign bit, replace this with a LT or GE comparison of
	     the underlying value.  */
	  if (equality_comparison_p
	      && const_op == 0
	      && CONST_INT_P (XEXP (op0, 1))
	      && mode_width <= HOST_BITS_PER_WIDE_INT
	      && ((INTVAL (XEXP (op0, 1)) & GET_MODE_MASK (mode))
		  == HOST_WIDE_INT_1U << (mode_width - 1)))
	    {
	      op0 = XEXP (op0, 0);
	      code = (code == EQ ? GE : LT);
	      continue;
	    }

	  /* If this AND operation is really a ZERO_EXTEND from a narrower
	     mode, the constant fits within that mode, and this is either an
	     equality or unsigned comparison, try to do this comparison in
	     the narrower mode.

	     Note that in:

	     (ne:DI (and:DI (reg:DI 4) (const_int 0xffffffff)) (const_int 0))
	     -> (ne:DI (reg:SI 4) (const_int 0))

	     unless TARGET_TRULY_NOOP_TRUNCATION allows it or the register is
	     known to hold a value of the required mode the
	     transformation is invalid.  */
	  if ((equality_comparison_p || unsigned_comparison_p)
	      && CONST_INT_P (XEXP (op0, 1))
	      && (i = exact_log2 ((UINTVAL (XEXP (op0, 1))
				   & GET_MODE_MASK (mode))
				  + 1)) >= 0
	      && const_op >> i == 0
	      && int_mode_for_size (i, 1).exists (&tmode))
	    {
	      op0 = gen_lowpart_or_truncate (tmode, XEXP (op0, 0));
	      continue;
	    }

	  /* If this is (and:M1 (subreg:M1 X:M2 0) (const_int C1)) where C1
	     fits in both M1 and M2 and the SUBREG is either paradoxical
	     or represents the low part, permute the SUBREG and the AND
	     and try again.  */
	  if (GET_CODE (XEXP (op0, 0)) == SUBREG
	      && CONST_INT_P (XEXP (op0, 1)))
	    {
	      unsigned HOST_WIDE_INT c1 = INTVAL (XEXP (op0, 1));
	      /* Require an integral mode, to avoid creating something like
		 (AND:SF ...).  */
	      if ((is_a <scalar_int_mode>
		   (GET_MODE (SUBREG_REG (XEXP (op0, 0))), &tmode))
		  /* It is unsafe to commute the AND into the SUBREG if the
		     SUBREG is paradoxical and WORD_REGISTER_OPERATIONS is
		     not defined.  As originally written the upper bits
		     have a defined value due to the AND operation.
		     However, if we commute the AND inside the SUBREG then
		     they no longer have defined values and the meaning of
		     the code has been changed.
		     Also C1 should not change value in the smaller mode,
		     see PR67028 (a positive C1 can become negative in the
		     smaller mode, so that the AND does no longer mask the
		     upper bits).  */
		  && ((WORD_REGISTER_OPERATIONS
		       && mode_width > GET_MODE_PRECISION (tmode)
		       && mode_width <= BITS_PER_WORD
		       && trunc_int_for_mode (c1, tmode) == (HOST_WIDE_INT) c1)
		      || (mode_width <= GET_MODE_PRECISION (tmode)
			  && subreg_lowpart_p (XEXP (op0, 0))))
		  && mode_width <= HOST_BITS_PER_WIDE_INT
		  && HWI_COMPUTABLE_MODE_P (tmode)
		  && (c1 & ~mask) == 0
		  && (c1 & ~GET_MODE_MASK (tmode)) == 0
		  && c1 != mask
		  && c1 != GET_MODE_MASK (tmode))
		{
		  op0 = simplify_gen_binary (AND, tmode,
					     SUBREG_REG (XEXP (op0, 0)),
					     gen_int_mode (c1, tmode));
		  op0 = gen_lowpart (mode, op0);
		  continue;
		}
	    }

	  /* Convert (ne (and (not X) 1) 0) to (eq (and X 1) 0).  */
	  if (const_op == 0 && equality_comparison_p
	      && XEXP (op0, 1) == const1_rtx
	      && GET_CODE (XEXP (op0, 0)) == NOT)
	    {
	      op0 = simplify_and_const_int (NULL_RTX, mode,
					    XEXP (XEXP (op0, 0), 0), 1);
	      code = (code == NE ? EQ : NE);
	      continue;
	    }

	  /* Convert (ne (and (lshiftrt (not X)) 1) 0) to
	     (eq (and (lshiftrt X) 1) 0).
	     Also handle the case where (not X) is expressed using xor.  */
	  if (const_op == 0 && equality_comparison_p
	      && XEXP (op0, 1) == const1_rtx
	      && GET_CODE (XEXP (op0, 0)) == LSHIFTRT)
	    {
	      rtx shift_op = XEXP (XEXP (op0, 0), 0);
	      rtx shift_count = XEXP (XEXP (op0, 0), 1);

	      if (GET_CODE (shift_op) == NOT
		  || (GET_CODE (shift_op) == XOR
		      && CONST_INT_P (XEXP (shift_op, 1))
		      && CONST_INT_P (shift_count)
		      && HWI_COMPUTABLE_MODE_P (mode)
		      && (UINTVAL (XEXP (shift_op, 1))
			  == HOST_WIDE_INT_1U
			       << INTVAL (shift_count))))
		{
		  op0
		    = gen_rtx_LSHIFTRT (mode, XEXP (shift_op, 0), shift_count);
		  op0 = simplify_and_const_int (NULL_RTX, mode, op0, 1);
		  code = (code == NE ? EQ : NE);
		  continue;
		}
	    }
	  break;

	case ASHIFT:
	  /* If we have (compare (ashift FOO N) (const_int C)) and
	     the high order N bits of FOO (N+1 if an inequality comparison)
	     are known to be zero, we can do this by comparing FOO with C
	     shifted right N bits so long as the low-order N bits of C are
	     zero.  */
	  if (CONST_INT_P (XEXP (op0, 1))
	      && INTVAL (XEXP (op0, 1)) >= 0
	      && ((INTVAL (XEXP (op0, 1)) + ! equality_comparison_p)
		  < HOST_BITS_PER_WIDE_INT)
	      && (((unsigned HOST_WIDE_INT) const_op
		   & ((HOST_WIDE_INT_1U << INTVAL (XEXP (op0, 1)))
		      - 1)) == 0)
	      && mode_width <= HOST_BITS_PER_WIDE_INT
	      && (nonzero_bits (XEXP (op0, 0), mode)
		  & ~(mask >> (INTVAL (XEXP (op0, 1))
			       + ! equality_comparison_p))) == 0)
	    {
	      /* We must perform a logical shift, not an arithmetic one,
		 as we want the top N bits of C to be zero.  */
	      unsigned HOST_WIDE_INT temp = const_op & GET_MODE_MASK (mode);

	      temp >>= INTVAL (XEXP (op0, 1));
	      op1 = gen_int_mode (temp, mode);
	      op0 = XEXP (op0, 0);
	      continue;
	    }

	  /* If we are doing a sign bit comparison, it means we are testing
	     a particular bit.  Convert it to the appropriate AND.  */
	  if (sign_bit_comparison_p && CONST_INT_P (XEXP (op0, 1))
	      && mode_width <= HOST_BITS_PER_WIDE_INT)
	    {
	      op0 = simplify_and_const_int (NULL_RTX, mode, XEXP (op0, 0),
					    (HOST_WIDE_INT_1U
					     << (mode_width - 1
						 - INTVAL (XEXP (op0, 1)))));
	      code = (code == LT ? NE : EQ);
	      continue;
	    }

	  /* If this an equality comparison with zero and we are shifting
	     the low bit to the sign bit, we can convert this to an AND of the
	     low-order bit.  */
	  if (const_op == 0 && equality_comparison_p
	      && CONST_INT_P (XEXP (op0, 1))
	      && UINTVAL (XEXP (op0, 1)) == mode_width - 1)
	    {
	      op0 = simplify_and_const_int (NULL_RTX, mode, XEXP (op0, 0), 1);
	      continue;
	    }
	  break;

	case ASHIFTRT:
	  /* If this is an equality comparison with zero, we can do this
	     as a logical shift, which might be much simpler.  */
	  if (equality_comparison_p && const_op == 0
	      && CONST_INT_P (XEXP (op0, 1)))
	    {
	      op0 = simplify_shift_const (NULL_RTX, LSHIFTRT, mode,
					  XEXP (op0, 0),
					  INTVAL (XEXP (op0, 1)));
	      continue;
	    }

	  /* If OP0 is a sign extension and CODE is not an unsigned comparison,
	     do the comparison in a narrower mode.  */
	  if (! unsigned_comparison_p
	      && CONST_INT_P (XEXP (op0, 1))
	      && GET_CODE (XEXP (op0, 0)) == ASHIFT
	      && XEXP (op0, 1) == XEXP (XEXP (op0, 0), 1)
	      && (int_mode_for_size (mode_width - INTVAL (XEXP (op0, 1)), 1)
		  .exists (&tmode))
	      && (((unsigned HOST_WIDE_INT) const_op
		   + (GET_MODE_MASK (tmode) >> 1) + 1)
		  <= GET_MODE_MASK (tmode)))
	    {
	      op0 = gen_lowpart (tmode, XEXP (XEXP (op0, 0), 0));
	      continue;
	    }

	  /* Likewise if OP0 is a PLUS of a sign extension with a
	     constant, which is usually represented with the PLUS
	     between the shifts.  */
	  if (! unsigned_comparison_p
	      && CONST_INT_P (XEXP (op0, 1))
	      && GET_CODE (XEXP (op0, 0)) == PLUS
	      && CONST_INT_P (XEXP (XEXP (op0, 0), 1))
	      && GET_CODE (XEXP (XEXP (op0, 0), 0)) == ASHIFT
	      && XEXP (op0, 1) == XEXP (XEXP (XEXP (op0, 0), 0), 1)
	      && (int_mode_for_size (mode_width - INTVAL (XEXP (op0, 1)), 1)
		  .exists (&tmode))
	      && (((unsigned HOST_WIDE_INT) const_op
		   + (GET_MODE_MASK (tmode) >> 1) + 1)
		  <= GET_MODE_MASK (tmode)))
	    {
	      rtx inner = XEXP (XEXP (XEXP (op0, 0), 0), 0);
	      rtx add_const = XEXP (XEXP (op0, 0), 1);
	      rtx new_const = simplify_gen_binary (ASHIFTRT, mode,
						   add_const, XEXP (op0, 1));

	      op0 = simplify_gen_binary (PLUS, tmode,
					 gen_lowpart (tmode, inner),
					 new_const);
	      continue;
	    }

	  /* FALLTHROUGH */
	case LSHIFTRT:
	  /* If we have (compare (xshiftrt FOO N) (const_int C)) and
	     the low order N bits of FOO are known to be zero, we can do this
	     by comparing FOO with C shifted left N bits so long as no
	     overflow occurs.  Even if the low order N bits of FOO aren't known
	     to be zero, if the comparison is >= or < we can use the same
	     optimization and for > or <= by setting all the low
	     order N bits in the comparison constant.  */
	  if (CONST_INT_P (XEXP (op0, 1))
	      && INTVAL (XEXP (op0, 1)) > 0
	      && INTVAL (XEXP (op0, 1)) < HOST_BITS_PER_WIDE_INT
	      && mode_width <= HOST_BITS_PER_WIDE_INT
	      && (((unsigned HOST_WIDE_INT) const_op
		   + (GET_CODE (op0) != LSHIFTRT
		      ? ((GET_MODE_MASK (mode) >> INTVAL (XEXP (op0, 1)) >> 1)
			 + 1)
		      : 0))
		  <= GET_MODE_MASK (mode) >> INTVAL (XEXP (op0, 1))))
	    {
	      unsigned HOST_WIDE_INT low_bits
		= (nonzero_bits (XEXP (op0, 0), mode)
		   & ((HOST_WIDE_INT_1U
		       << INTVAL (XEXP (op0, 1))) - 1));
	      if (low_bits == 0 || !equality_comparison_p)
		{
		  /* If the shift was logical, then we must make the condition
		     unsigned.  */
		  if (GET_CODE (op0) == LSHIFTRT)
		    code = unsigned_condition (code);

		  const_op = (unsigned HOST_WIDE_INT) const_op
			      << INTVAL (XEXP (op0, 1));
		  if (low_bits != 0
		      && (code == GT || code == GTU
			  || code == LE || code == LEU))
		    const_op
		      |= ((HOST_WIDE_INT_1 << INTVAL (XEXP (op0, 1))) - 1);
		  op1 = GEN_INT (const_op);
		  op0 = XEXP (op0, 0);
		  continue;
		}
	    }

	  /* If we are using this shift to extract just the sign bit, we
	     can replace this with an LT or GE comparison.  */
	  if (const_op == 0
	      && (equality_comparison_p || sign_bit_comparison_p)
	      && CONST_INT_P (XEXP (op0, 1))
	      && UINTVAL (XEXP (op0, 1)) == mode_width - 1)
	    {
	      op0 = XEXP (op0, 0);
	      code = (code == NE || code == GT ? LT : GE);
	      continue;
	    }
	  break;

	default:
	  break;
	}

      break;
    }

  /* Now make any compound operations involved in this comparison.  Then,
     check for an outmost SUBREG on OP0 that is not doing anything or is
     paradoxical.  The latter transformation must only be performed when
     it is known that the "extra" bits will be the same in op0 and op1 or
     that they don't matter.  There are three cases to consider:

     1. SUBREG_REG (op0) is a register.  In this case the bits are don't
     care bits and we can assume they have any convenient value.  So
     making the transformation is safe.

     2. SUBREG_REG (op0) is a memory and LOAD_EXTEND_OP is UNKNOWN.
     In this case the upper bits of op0 are undefined.  We should not make
     the simplification in that case as we do not know the contents of
     those bits.

     3. SUBREG_REG (op0) is a memory and LOAD_EXTEND_OP is not UNKNOWN.
     In that case we know those bits are zeros or ones.  We must also be
     sure that they are the same as the upper bits of op1.

     We can never remove a SUBREG for a non-equality comparison because
     the sign bit is in a different place in the underlying object.  */

  rtx_code op0_mco_code = SET;
  if (op1 == const0_rtx)
    op0_mco_code = code == NE || code == EQ ? EQ : COMPARE;

  op0 = make_compound_operation (op0, op0_mco_code);
  op1 = make_compound_operation (op1, SET);

  if (GET_CODE (op0) == SUBREG && subreg_lowpart_p (op0)
      && is_int_mode (GET_MODE (op0), &mode)
      && is_int_mode (GET_MODE (SUBREG_REG (op0)), &inner_mode)
      && (code == NE || code == EQ))
    {
      if (paradoxical_subreg_p (op0))
	{
	  /* For paradoxical subregs, allow case 1 as above.  Case 3 isn't
	     implemented.  */
	  if (REG_P (SUBREG_REG (op0)))
	    {
	      op0 = SUBREG_REG (op0);
	      op1 = gen_lowpart (inner_mode, op1);
	    }
	}
      else if (GET_MODE_PRECISION (inner_mode) <= HOST_BITS_PER_WIDE_INT
	       && (nonzero_bits (SUBREG_REG (op0), inner_mode)
		   & ~GET_MODE_MASK (mode)) == 0)
	{
	  tem = gen_lowpart (inner_mode, op1);

	  if ((nonzero_bits (tem, inner_mode) & ~GET_MODE_MASK (mode)) == 0)
	    op0 = SUBREG_REG (op0), op1 = tem;
	}
    }

  /* We now do the opposite procedure: Some machines don't have compare
     insns in all modes.  If OP0's mode is an integer mode smaller than a
     word and we can't do a compare in that mode, see if there is a larger
     mode for which we can do the compare.  There are a number of cases in
     which we can use the wider mode.  */

  if (is_int_mode (GET_MODE (op0), &mode)
      && GET_MODE_SIZE (mode) < UNITS_PER_WORD
      && ! have_insn_for (COMPARE, mode))
    FOR_EACH_WIDER_MODE (tmode_iter, mode)
      {
	tmode = tmode_iter.require ();
	if (!HWI_COMPUTABLE_MODE_P (tmode))
	  break;
	if (have_insn_for (COMPARE, tmode))
	  {
	    int zero_extended;

	    /* If this is a test for negative, we can make an explicit
	       test of the sign bit.  Test this first so we can use
	       a paradoxical subreg to extend OP0.  */

	    if (op1 == const0_rtx && (code == LT || code == GE)
		&& HWI_COMPUTABLE_MODE_P (mode))
	      {
		unsigned HOST_WIDE_INT sign
		  = HOST_WIDE_INT_1U << (GET_MODE_BITSIZE (mode) - 1);
		op0 = simplify_gen_binary (AND, tmode,
					   gen_lowpart (tmode, op0),
					   gen_int_mode (sign, tmode));
		code = (code == LT) ? NE : EQ;
		break;
	      }

	    /* If the only nonzero bits in OP0 and OP1 are those in the
	       narrower mode and this is an equality or unsigned comparison,
	       we can use the wider mode.  Similarly for sign-extended
	       values, in which case it is true for all comparisons.  */
	    zero_extended = ((code == EQ || code == NE
			      || code == GEU || code == GTU
			      || code == LEU || code == LTU)
			     && (nonzero_bits (op0, tmode)
				 & ~GET_MODE_MASK (mode)) == 0
			     && ((CONST_INT_P (op1)
				  || (nonzero_bits (op1, tmode)
				      & ~GET_MODE_MASK (mode)) == 0)));

	    if (zero_extended
		|| ((num_sign_bit_copies (op0, tmode)
		     > (unsigned int) (GET_MODE_PRECISION (tmode)
				       - GET_MODE_PRECISION (mode)))
		    && (num_sign_bit_copies (op1, tmode)
			> (unsigned int) (GET_MODE_PRECISION (tmode)
					  - GET_MODE_PRECISION (mode)))))
	      {
		/* If OP0 is an AND and we don't have an AND in MODE either,
		   make a new AND in the proper mode.  */
		if (GET_CODE (op0) == AND
		    && !have_insn_for (AND, mode))
		  op0 = simplify_gen_binary (AND, tmode,
					     gen_lowpart (tmode,
							  XEXP (op0, 0)),
					     gen_lowpart (tmode,
							  XEXP (op0, 1)));
		else
		  {
		    if (zero_extended)
		      {
			op0 = simplify_gen_unary (ZERO_EXTEND, tmode,
						  op0, mode);
			op1 = simplify_gen_unary (ZERO_EXTEND, tmode,
						  op1, mode);
		      }
		    else
		      {
			op0 = simplify_gen_unary (SIGN_EXTEND, tmode,
						  op0, mode);
			op1 = simplify_gen_unary (SIGN_EXTEND, tmode,
						  op1, mode);
		      }
		    break;
		  }
	      }
	  }
      }

  /* We may have changed the comparison operands.  Re-canonicalize.  */
  if (swap_commutative_operands_p (op0, op1))
    {
      std::swap (op0, op1);
      code = swap_condition (code);
    }

  /* If this machine only supports a subset of valid comparisons, see if we
     can convert an unsupported one into a supported one.  */
  target_canonicalize_comparison (&code, &op0, &op1, 0);

  *pop0 = op0;
  *pop1 = op1;

  return code;
}

/* Utility function for record_value_for_reg.  Count number of
   rtxs in X.  */
static int
count_rtxs (rtx x)
{
  enum rtx_code code = GET_CODE (x);
  const char *fmt;
  int i, j, ret = 1;

  if (GET_RTX_CLASS (code) == RTX_BIN_ARITH
      || GET_RTX_CLASS (code) == RTX_COMM_ARITH)
    {
      rtx x0 = XEXP (x, 0);
      rtx x1 = XEXP (x, 1);

      if (x0 == x1)
	return 1 + 2 * count_rtxs (x0);

      if ((GET_RTX_CLASS (GET_CODE (x1)) == RTX_BIN_ARITH
	   || GET_RTX_CLASS (GET_CODE (x1)) == RTX_COMM_ARITH)
	  && (x0 == XEXP (x1, 0) || x0 == XEXP (x1, 1)))
	return 2 + 2 * count_rtxs (x0)
	       + count_rtxs (x == XEXP (x1, 0)
			     ? XEXP (x1, 1) : XEXP (x1, 0));

      if ((GET_RTX_CLASS (GET_CODE (x0)) == RTX_BIN_ARITH
	   || GET_RTX_CLASS (GET_CODE (x0)) == RTX_COMM_ARITH)
	  && (x1 == XEXP (x0, 0) || x1 == XEXP (x0, 1)))
	return 2 + 2 * count_rtxs (x1)
	       + count_rtxs (x == XEXP (x0, 0)
			     ? XEXP (x0, 1) : XEXP (x0, 0));
    }

  fmt = GET_RTX_FORMAT (code);
  for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
    if (fmt[i] == 'e')
      ret += count_rtxs (XEXP (x, i));
    else if (fmt[i] == 'E')
      for (j = 0; j < XVECLEN (x, i); j++)
	ret += count_rtxs (XVECEXP (x, i, j));

  return ret;
}

/* Utility function for following routine.  Called when X is part of a value
   being stored into last_set_value.  Sets last_set_table_tick
   for each register mentioned.  Similar to mention_regs in cse.c  */

static void
update_table_tick (rtx x)
{
  enum rtx_code code = GET_CODE (x);
  const char *fmt = GET_RTX_FORMAT (code);
  int i, j;

  if (code == REG)
    {
      unsigned int regno = REGNO (x);
      unsigned int endregno = END_REGNO (x);
      unsigned int r;

      for (r = regno; r < endregno; r++)
	{
	  reg_stat_type *rsp = &reg_stat[r];
	  rsp->last_set_table_tick = label_tick;
	}

      return;
    }

  for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
    if (fmt[i] == 'e')
      {
	/* Check for identical subexpressions.  If x contains
	   identical subexpression we only have to traverse one of
	   them.  */
	if (i == 0 && ARITHMETIC_P (x))
	  {
	    /* Note that at this point x1 has already been
	       processed.  */
	    rtx x0 = XEXP (x, 0);
	    rtx x1 = XEXP (x, 1);

	    /* If x0 and x1 are identical then there is no need to
	       process x0.  */
	    if (x0 == x1)
	      break;

	    /* If x0 is identical to a subexpression of x1 then while
	       processing x1, x0 has already been processed.  Thus we
	       are done with x.  */
	    if (ARITHMETIC_P (x1)
		&& (x0 == XEXP (x1, 0) || x0 == XEXP (x1, 1)))
	      break;

	    /* If x1 is identical to a subexpression of x0 then we
	       still have to process the rest of x0.  */
	    if (ARITHMETIC_P (x0)
		&& (x1 == XEXP (x0, 0) || x1 == XEXP (x0, 1)))
	      {
		update_table_tick (XEXP (x0, x1 == XEXP (x0, 0) ? 1 : 0));
		break;
	      }
	  }

	update_table_tick (XEXP (x, i));
      }
    else if (fmt[i] == 'E')
      for (j = 0; j < XVECLEN (x, i); j++)
	update_table_tick (XVECEXP (x, i, j));
}

/* Record that REG is set to VALUE in insn INSN.  If VALUE is zero, we
   are saying that the register is clobbered and we no longer know its
   value.  If INSN is zero, don't update reg_stat[].last_set; this is
   only permitted with VALUE also zero and is used to invalidate the
   register.  */

static void
record_value_for_reg (rtx reg, rtx_insn *insn, rtx value)
{
  unsigned int regno = REGNO (reg);
  unsigned int endregno = END_REGNO (reg);
  unsigned int i;
  reg_stat_type *rsp;

  /* If VALUE contains REG and we have a previous value for REG, substitute
     the previous value.  */
  if (value && insn && reg_overlap_mentioned_p (reg, value))
    {
      rtx tem;

      /* Set things up so get_last_value is allowed to see anything set up to
	 our insn.  */
      subst_low_luid = DF_INSN_LUID (insn);
      tem = get_last_value (reg);

      /* If TEM is simply a binary operation with two CLOBBERs as operands,
	 it isn't going to be useful and will take a lot of time to process,
	 so just use the CLOBBER.  */

      if (tem)
	{
	  if (ARITHMETIC_P (tem)
	      && GET_CODE (XEXP (tem, 0)) == CLOBBER
	      && GET_CODE (XEXP (tem, 1)) == CLOBBER)
	    tem = XEXP (tem, 0);
	  else if (count_occurrences (value, reg, 1) >= 2)
	    {
	      /* If there are two or more occurrences of REG in VALUE,
		 prevent the value from growing too much.  */
	      if (count_rtxs (tem) > MAX_LAST_VALUE_RTL)
		tem = gen_rtx_CLOBBER (GET_MODE (tem), const0_rtx);
	    }

	  value = replace_rtx (copy_rtx (value), reg, tem);
	}
    }

  /* For each register modified, show we don't know its value, that
     we don't know about its bitwise content, that its value has been
     updated, and that we don't know the location of the death of the
     register.  */
  for (i = regno; i < endregno; i++)
    {
      rsp = &reg_stat[i];

      if (insn)
	rsp->last_set = insn;

      rsp->last_set_value = 0;
      rsp->last_set_mode = VOIDmode;
      rsp->last_set_nonzero_bits = 0;
      rsp->last_set_sign_bit_copies = 0;
      rsp->last_death = 0;
      rsp->truncated_to_mode = VOIDmode;
    }

  /* Mark registers that are being referenced in this value.  */
  if (value)
    update_table_tick (value);

  /* Now update the status of each register being set.
     If someone is using this register in this block, set this register
     to invalid since we will get confused between the two lives in this
     basic block.  This makes using this register always invalid.  In cse, we
     scan the table to invalidate all entries using this register, but this
     is too much work for us.  */

  for (i = regno; i < endregno; i++)
    {
      rsp = &reg_stat[i];
      rsp->last_set_label = label_tick;
      if (!insn
	  || (value && rsp->last_set_table_tick >= label_tick_ebb_start))
	rsp->last_set_invalid = 1;
      else
	rsp->last_set_invalid = 0;
    }

  /* The value being assigned might refer to X (like in "x++;").  In that
     case, we must replace it with (clobber (const_int 0)) to prevent
     infinite loops.  */
  rsp = &reg_stat[regno];
  if (value && !get_last_value_validate (&value, insn, label_tick, 0))
    {
      value = copy_rtx (value);
      if (!get_last_value_validate (&value, insn, label_tick, 1))
	value = 0;
    }

  /* For the main register being modified, update the value, the mode, the
     nonzero bits, and the number of sign bit copies.  */

  rsp->last_set_value = value;

  if (value)
    {
      machine_mode mode = GET_MODE (reg);
      subst_low_luid = DF_INSN_LUID (insn);
      rsp->last_set_mode = mode;
      if (GET_MODE_CLASS (mode) == MODE_INT
	  && HWI_COMPUTABLE_MODE_P (mode))
	mode = nonzero_bits_mode;
      rsp->last_set_nonzero_bits = nonzero_bits (value, mode);
      rsp->last_set_sign_bit_copies
	= num_sign_bit_copies (value, GET_MODE (reg));
    }
}

/* Called via note_stores from record_dead_and_set_regs to handle one
   SET or CLOBBER in an insn.  DATA is the instruction in which the
   set is occurring.  */

static void
record_dead_and_set_regs_1 (rtx dest, const_rtx setter, void *data)
{
  rtx_insn *record_dead_insn = (rtx_insn *) data;

  if (GET_CODE (dest) == SUBREG)
    dest = SUBREG_REG (dest);

  if (!record_dead_insn)
    {
      if (REG_P (dest))
	record_value_for_reg (dest, NULL, NULL_RTX);
      return;
    }

  if (REG_P (dest))
    {
      /* If we are setting the whole register, we know its value.  Otherwise
	 show that we don't know the value.  We can handle a SUBREG if it's
	 the low part, but we must be careful with paradoxical SUBREGs on
	 RISC architectures because we cannot strip e.g. an extension around
	 a load and record the naked load since the RTL middle-end considers
	 that the upper bits are defined according to LOAD_EXTEND_OP.  */
      if (GET_CODE (setter) == SET && dest == SET_DEST (setter))
	record_value_for_reg (dest, record_dead_insn, SET_SRC (setter));
      else if (GET_CODE (setter) == SET
	       && GET_CODE (SET_DEST (setter)) == SUBREG
	       && SUBREG_REG (SET_DEST (setter)) == dest
	       && known_le (GET_MODE_PRECISION (GET_MODE (dest)),
			    BITS_PER_WORD)
	       && subreg_lowpart_p (SET_DEST (setter)))
	record_value_for_reg (dest, record_dead_insn,
			      WORD_REGISTER_OPERATIONS
			      && paradoxical_subreg_p (SET_DEST (setter))
			      ? SET_SRC (setter)
			      : gen_lowpart (GET_MODE (dest),
					     SET_SRC (setter)));
      else if (GET_CODE (setter) == CLOBBER_HIGH)
	{
	  reg_stat_type *rsp = &reg_stat[REGNO (dest)];
	  if (rsp->last_set_value
	      && reg_is_clobbered_by_clobber_high
		   (REGNO (dest), GET_MODE (rsp->last_set_value),
		    XEXP (setter, 0)))
	    record_value_for_reg (dest, NULL, NULL_RTX);
	}
      else
	record_value_for_reg (dest, record_dead_insn, NULL_RTX);
    }
  else if (MEM_P (dest)
	   /* Ignore pushes, they clobber nothing.  */
	   && ! push_operand (dest, GET_MODE (dest)))
    mem_last_set = DF_INSN_LUID (record_dead_insn);
}

/* Update the records of when each REG was most recently set or killed
   for the things done by INSN.  This is the last thing done in processing
   INSN in the combiner loop.

   We update reg_stat[], in particular fields last_set, last_set_value,
   last_set_mode, last_set_nonzero_bits, last_set_sign_bit_copies,
   last_death, and also the similar information mem_last_set (which insn
   most recently modified memory) and last_call_luid (which insn was the
   most recent subroutine call).  */

static void
record_dead_and_set_regs (rtx_insn *insn)
{
  rtx link;
  unsigned int i;

  for (link = REG_NOTES (insn); link; link = XEXP (link, 1))
    {
      if (REG_NOTE_KIND (link) == REG_DEAD
	  && REG_P (XEXP (link, 0)))
	{
	  unsigned int regno = REGNO (XEXP (link, 0));
	  unsigned int endregno = END_REGNO (XEXP (link, 0));

	  for (i = regno; i < endregno; i++)
	    {
	      reg_stat_type *rsp;

	      rsp = &reg_stat[i];
	      rsp->last_death = insn;
	    }
	}
      else if (REG_NOTE_KIND (link) == REG_INC)
	record_value_for_reg (XEXP (link, 0), insn, NULL_RTX);
    }

  if (CALL_P (insn))
    {
      hard_reg_set_iterator hrsi;
      EXECUTE_IF_SET_IN_HARD_REG_SET (regs_invalidated_by_call, 0, i, hrsi)
	{
	  reg_stat_type *rsp;

	  rsp = &reg_stat[i];
	  rsp->last_set_invalid = 1;
	  rsp->last_set = insn;
	  rsp->last_set_value = 0;
	  rsp->last_set_mode = VOIDmode;
	  rsp->last_set_nonzero_bits = 0;
	  rsp->last_set_sign_bit_copies = 0;
	  rsp->last_death = 0;
	  rsp->truncated_to_mode = VOIDmode;
	}

      last_call_luid = mem_last_set = DF_INSN_LUID (insn);

      /* We can't combine into a call pattern.  Remember, though, that
	 the return value register is set at this LUID.  We could
	 still replace a register with the return value from the
	 wrong subroutine call!  */
      note_stores (PATTERN (insn), record_dead_and_set_regs_1, NULL_RTX);
    }
  else
    note_stores (PATTERN (insn), record_dead_and_set_regs_1, insn);
}

/* If a SUBREG has the promoted bit set, it is in fact a property of the
   register present in the SUBREG, so for each such SUBREG go back and
   adjust nonzero and sign bit information of the registers that are
   known to have some zero/sign bits set.

   This is needed because when combine blows the SUBREGs away, the
   information on zero/sign bits is lost and further combines can be
   missed because of that.  */

static void
record_promoted_value (rtx_insn *insn, rtx subreg)
{
  struct insn_link *links;
  rtx set;
  unsigned int regno = REGNO (SUBREG_REG (subreg));
  machine_mode mode = GET_MODE (subreg);

  if (!HWI_COMPUTABLE_MODE_P (mode))
    return;

  for (links = LOG_LINKS (insn); links;)
    {
      reg_stat_type *rsp;

      insn = links->insn;
      set = single_set (insn);

      if (! set || !REG_P (SET_DEST (set))
	  || REGNO (SET_DEST (set)) != regno
	  || GET_MODE (SET_DEST (set)) != GET_MODE (SUBREG_REG (subreg)))
	{
	  links = links->next;
	  continue;
	}

      rsp = &reg_stat[regno];
      if (rsp->last_set == insn)
	{
	  if (SUBREG_PROMOTED_UNSIGNED_P (subreg))
	    rsp->last_set_nonzero_bits &= GET_MODE_MASK (mode);
	}

      if (REG_P (SET_SRC (set)))
	{
	  regno = REGNO (SET_SRC (set));
	  links = LOG_LINKS (insn);
	}
      else
	break;
    }
}

/* Check if X, a register, is known to contain a value already
   truncated to MODE.  In this case we can use a subreg to refer to
   the truncated value even though in the generic case we would need
   an explicit truncation.  */

static bool
reg_truncated_to_mode (machine_mode mode, const_rtx x)
{
  reg_stat_type *rsp = &reg_stat[REGNO (x)];
  machine_mode truncated = rsp->truncated_to_mode;

  if (truncated == 0
      || rsp->truncation_label < label_tick_ebb_start)
    return false;
  if (!partial_subreg_p (mode, truncated))
    return true;
  if (TRULY_NOOP_TRUNCATION_MODES_P (mode, truncated))
    return true;
  return false;
}

/* If X is a hard reg or a subreg record the mode that the register is
   accessed in.  For non-TARGET_TRULY_NOOP_TRUNCATION targets we might be
   able to turn a truncate into a subreg using this information.  Return true
   if traversing X is complete.  */

static bool
record_truncated_value (rtx x)
{
  machine_mode truncated_mode;
  reg_stat_type *rsp;

  if (GET_CODE (x) == SUBREG && REG_P (SUBREG_REG (x)))
    {
      machine_mode original_mode = GET_MODE (SUBREG_REG (x));
      truncated_mode = GET_MODE (x);

      if (!partial_subreg_p (truncated_mode, original_mode))
	return true;

      truncated_mode = GET_MODE (x);
      if (TRULY_NOOP_TRUNCATION_MODES_P (truncated_mode, original_mode))
	return true;

      x = SUBREG_REG (x);
    }
  /* ??? For hard-regs we now record everything.  We might be able to
     optimize this using last_set_mode.  */
  else if (REG_P (x) && REGNO (x) < FIRST_PSEUDO_REGISTER)
    truncated_mode = GET_MODE (x);
  else
    return false;

  rsp = &reg_stat[REGNO (x)];
  if (rsp->truncated_to_mode == 0
      || rsp->truncation_label < label_tick_ebb_start
      || partial_subreg_p (truncated_mode, rsp->truncated_to_mode))
    {
      rsp->truncated_to_mode = truncated_mode;
      rsp->truncation_label = label_tick;
    }

  return true;
}

/* Callback for note_uses.  Find hardregs and subregs of pseudos and
   the modes they are used in.  This can help truning TRUNCATEs into
   SUBREGs.  */

static void
record_truncated_values (rtx *loc, void *data ATTRIBUTE_UNUSED)
{
  subrtx_var_iterator::array_type array;
  FOR_EACH_SUBRTX_VAR (iter, array, *loc, NONCONST)
    if (record_truncated_value (*iter))
      iter.skip_subrtxes ();
}

/* Scan X for promoted SUBREGs.  For each one found,
   note what it implies to the registers used in it.  */

static void
check_promoted_subreg (rtx_insn *insn, rtx x)
{
  if (GET_CODE (x) == SUBREG
      && SUBREG_PROMOTED_VAR_P (x)
      && REG_P (SUBREG_REG (x)))
    record_promoted_value (insn, x);
  else
    {
      const char *format = GET_RTX_FORMAT (GET_CODE (x));
      int i, j;

      for (i = 0; i < GET_RTX_LENGTH (GET_CODE (x)); i++)
	switch (format[i])
	  {
	  case 'e':
	    check_promoted_subreg (insn, XEXP (x, i));
	    break;
	  case 'V':
	  case 'E':
	    if (XVEC (x, i) != 0)
	      for (j = 0; j < XVECLEN (x, i); j++)
		check_promoted_subreg (insn, XVECEXP (x, i, j));
	    break;
	  }
    }
}

/* Verify that all the registers and memory references mentioned in *LOC are
   still valid.  *LOC was part of a value set in INSN when label_tick was
   equal to TICK.  Return 0 if some are not.  If REPLACE is nonzero, replace
   the invalid references with (clobber (const_int 0)) and return 1.  This
   replacement is useful because we often can get useful information about
   the form of a value (e.g., if it was produced by a shift that always
   produces -1 or 0) even though we don't know exactly what registers it
   was produced from.  */

static int
get_last_value_validate (rtx *loc, rtx_insn *insn, int tick, int replace)
{
  rtx x = *loc;
  const char *fmt = GET_RTX_FORMAT (GET_CODE (x));
  int len = GET_RTX_LENGTH (GET_CODE (x));
  int i, j;

  if (REG_P (x))
    {
      unsigned int regno = REGNO (x);
      unsigned int endregno = END_REGNO (x);
      unsigned int j;

      for (j = regno; j < endregno; j++)
	{
	  reg_stat_type *rsp = &reg_stat[j];
	  if (rsp->last_set_invalid
	      /* If this is a pseudo-register that was only set once and not
		 live at the beginning of the function, it is always valid.  */
	      || (! (regno >= FIRST_PSEUDO_REGISTER
		     && regno < reg_n_sets_max
		     && REG_N_SETS (regno) == 1
		     && (!REGNO_REG_SET_P
			 (DF_LR_IN (ENTRY_BLOCK_PTR_FOR_FN (cfun)->next_bb),
			  regno)))
		  && rsp->last_set_label > tick))
	  {
	    if (replace)
	      *loc = gen_rtx_CLOBBER (GET_MODE (x), const0_rtx);
	    return replace;
	  }
	}

      return 1;
    }
  /* If this is a memory reference, make sure that there were no stores after
     it that might have clobbered the value.  We don't have alias info, so we
     assume any store invalidates it.  Moreover, we only have local UIDs, so
     we also assume that there were stores in the intervening basic blocks.  */
  else if (MEM_P (x) && !MEM_READONLY_P (x)
	   && (tick != label_tick || DF_INSN_LUID (insn) <= mem_last_set))
    {
      if (replace)
	*loc = gen_rtx_CLOBBER (GET_MODE (x), const0_rtx);
      return replace;
    }

  for (i = 0; i < len; i++)
    {
      if (fmt[i] == 'e')
	{
	  /* Check for identical subexpressions.  If x contains
	     identical subexpression we only have to traverse one of
	     them.  */
	  if (i == 1 && ARITHMETIC_P (x))
	    {
	      /* Note that at this point x0 has already been checked
		 and found valid.  */
	      rtx x0 = XEXP (x, 0);
	      rtx x1 = XEXP (x, 1);

	      /* If x0 and x1 are identical then x is also valid.  */
	      if (x0 == x1)
		return 1;

	      /* If x1 is identical to a subexpression of x0 then
		 while checking x0, x1 has already been checked.  Thus
		 it is valid and so as x.  */
	      if (ARITHMETIC_P (x0)
		  && (x1 == XEXP (x0, 0) || x1 == XEXP (x0, 1)))
		return 1;

	      /* If x0 is identical to a subexpression of x1 then x is
		 valid iff the rest of x1 is valid.  */
	      if (ARITHMETIC_P (x1)
		  && (x0 == XEXP (x1, 0) || x0 == XEXP (x1, 1)))
		return
		  get_last_value_validate (&XEXP (x1,
						  x0 == XEXP (x1, 0) ? 1 : 0),
					   insn, tick, replace);
	    }

	  if (get_last_value_validate (&XEXP (x, i), insn, tick,
				       replace) == 0)
	    return 0;
	}
      else if (fmt[i] == 'E')
	for (j = 0; j < XVECLEN (x, i); j++)
	  if (get_last_value_validate (&XVECEXP (x, i, j),
				       insn, tick, replace) == 0)
	    return 0;
    }

  /* If we haven't found a reason for it to be invalid, it is valid.  */
  return 1;
}

/* Get the last value assigned to X, if known.  Some registers
   in the value may be replaced with (clobber (const_int 0)) if their value
   is known longer known reliably.  */

static rtx
get_last_value (const_rtx x)
{
  unsigned int regno;
  rtx value;
  reg_stat_type *rsp;

  /* If this is a non-paradoxical SUBREG, get the value of its operand and
     then convert it to the desired mode.  If this is a paradoxical SUBREG,
     we cannot predict what values the "extra" bits might have.  */
  if (GET_CODE (x) == SUBREG
      && subreg_lowpart_p (x)
      && !paradoxical_subreg_p (x)
      && (value = get_last_value (SUBREG_REG (x))) != 0)
    return gen_lowpart (GET_MODE (x), value);

  if (!REG_P (x))
    return 0;

  regno = REGNO (x);
  rsp = &reg_stat[regno];
  value = rsp->last_set_value;

  /* If we don't have a value, or if it isn't for this basic block and
     it's either a hard register, set more than once, or it's a live
     at the beginning of the function, return 0.

     Because if it's not live at the beginning of the function then the reg
     is always set before being used (is never used without being set).
     And, if it's set only once, and it's always set before use, then all
     uses must have the same last value, even if it's not from this basic
     block.  */

  if (value == 0
      || (rsp->last_set_label < label_tick_ebb_start
	  && (regno < FIRST_PSEUDO_REGISTER
	      || regno >= reg_n_sets_max
	      || REG_N_SETS (regno) != 1
	      || REGNO_REG_SET_P
		 (DF_LR_IN (ENTRY_BLOCK_PTR_FOR_FN (cfun)->next_bb), regno))))
    return 0;

  /* If the value was set in a later insn than the ones we are processing,
     we can't use it even if the register was only set once.  */
  if (rsp->last_set_label == label_tick
      && DF_INSN_LUID (rsp->last_set) >= subst_low_luid)
    return 0;

  /* If fewer bits were set than what we are asked for now, we cannot use
     the value.  */
  if (maybe_lt (GET_MODE_PRECISION (rsp->last_set_mode),
		GET_MODE_PRECISION (GET_MODE (x))))
    return 0;

  /* If the value has all its registers valid, return it.  */
  if (get_last_value_validate (&value, rsp->last_set, rsp->last_set_label, 0))
    return value;

  /* Otherwise, make a copy and replace any invalid register with
     (clobber (const_int 0)).  If that fails for some reason, return 0.  */

  value = copy_rtx (value);
  if (get_last_value_validate (&value, rsp->last_set, rsp->last_set_label, 1))
    return value;

  return 0;
}

/* Define three variables used for communication between the following
   routines.  */

static unsigned int reg_dead_regno, reg_dead_endregno;
static int reg_dead_flag;
rtx reg_dead_reg;

/* Function called via note_stores from reg_dead_at_p.

   If DEST is within [reg_dead_regno, reg_dead_endregno), set
   reg_dead_flag to 1 if X is a CLOBBER and to -1 it is a SET.  */

static void
reg_dead_at_p_1 (rtx dest, const_rtx x, void *data ATTRIBUTE_UNUSED)
{
  unsigned int regno, endregno;

  if (!REG_P (dest))
    return;

  if (GET_CODE (x) == CLOBBER_HIGH
      && !reg_is_clobbered_by_clobber_high (reg_dead_reg, XEXP (x, 0)))
    return;

  regno = REGNO (dest);
  endregno = END_REGNO (dest);
  if (reg_dead_endregno > regno && reg_dead_regno < endregno)
    reg_dead_flag = (GET_CODE (x) == CLOBBER) ? 1 : -1;
}

/* Return nonzero if REG is known to be dead at INSN.

   We scan backwards from INSN.  If we hit a REG_DEAD note or a CLOBBER
   referencing REG, it is dead.  If we hit a SET referencing REG, it is
   live.  Otherwise, see if it is live or dead at the start of the basic
   block we are in.  Hard regs marked as being live in NEWPAT_USED_REGS
   must be assumed to be always live.  */

static int
reg_dead_at_p (rtx reg, rtx_insn *insn)
{
  basic_block block;
  unsigned int i;

  /* Set variables for reg_dead_at_p_1.  */
  reg_dead_regno = REGNO (reg);
  reg_dead_endregno = END_REGNO (reg);
  reg_dead_reg = reg;

  reg_dead_flag = 0;

  /* Check that reg isn't mentioned in NEWPAT_USED_REGS.  For fixed registers
     we allow the machine description to decide whether use-and-clobber
     patterns are OK.  */
  if (reg_dead_regno < FIRST_PSEUDO_REGISTER)
    {
      for (i = reg_dead_regno; i < reg_dead_endregno; i++)
	if (!fixed_regs[i] && TEST_HARD_REG_BIT (newpat_used_regs, i))
	  return 0;
    }

  /* Scan backwards until we find a REG_DEAD note, SET, CLOBBER, or
     beginning of basic block.  */
  block = BLOCK_FOR_INSN (insn);
  for (;;)
    {
      if (INSN_P (insn))
        {
	  if (find_regno_note (insn, REG_UNUSED, reg_dead_regno))
	    return 1;

	  note_stores (PATTERN (insn), reg_dead_at_p_1, NULL);
	  if (reg_dead_flag)
	    return reg_dead_flag == 1 ? 1 : 0;

	  if (find_regno_note (insn, REG_DEAD, reg_dead_regno))
	    return 1;
        }

      if (insn == BB_HEAD (block))
	break;

      insn = PREV_INSN (insn);
    }

  /* Look at live-in sets for the basic block that we were in.  */
  for (i = reg_dead_regno; i < reg_dead_endregno; i++)
    if (REGNO_REG_SET_P (df_get_live_in (block), i))
      return 0;

  return 1;
}

/* Note hard registers in X that are used.  */

static void
mark_used_regs_combine (rtx x)
{
  RTX_CODE code = GET_CODE (x);
  unsigned int regno;
  int i;

  switch (code)
    {
    case LABEL_REF:
    case SYMBOL_REF:
    case CONST:
    CASE_CONST_ANY:
    case PC:
    case ADDR_VEC:
    case ADDR_DIFF_VEC:
    case ASM_INPUT:
    /* CC0 must die in the insn after it is set, so we don't need to take
       special note of it here.  */
    case CC0:
      return;

    case CLOBBER:
      /* If we are clobbering a MEM, mark any hard registers inside the
	 address as used.  */
      if (MEM_P (XEXP (x, 0)))
	mark_used_regs_combine (XEXP (XEXP (x, 0), 0));
      return;

    case REG:
      regno = REGNO (x);
      /* A hard reg in a wide mode may really be multiple registers.
	 If so, mark all of them just like the first.  */
      if (regno < FIRST_PSEUDO_REGISTER)
	{
	  /* None of this applies to the stack, frame or arg pointers.  */
	  if (regno == STACK_POINTER_REGNUM
	      || (!HARD_FRAME_POINTER_IS_FRAME_POINTER
		  && regno == HARD_FRAME_POINTER_REGNUM)
	      || (FRAME_POINTER_REGNUM != ARG_POINTER_REGNUM
		  && regno == ARG_POINTER_REGNUM && fixed_regs[regno])
	      || regno == FRAME_POINTER_REGNUM)
	    return;

	  add_to_hard_reg_set (&newpat_used_regs, GET_MODE (x), regno);
	}
      return;

    case SET:
      {
	/* If setting a MEM, or a SUBREG of a MEM, then note any hard regs in
	   the address.  */
	rtx testreg = SET_DEST (x);

	while (GET_CODE (testreg) == SUBREG
	       || GET_CODE (testreg) == ZERO_EXTRACT
	       || GET_CODE (testreg) == STRICT_LOW_PART)
	  testreg = XEXP (testreg, 0);

	if (MEM_P (testreg))
	  mark_used_regs_combine (XEXP (testreg, 0));

	mark_used_regs_combine (SET_SRC (x));
      }
      return;

    default:
      break;
    }

  /* Recursively scan the operands of this expression.  */

  {
    const char *fmt = GET_RTX_FORMAT (code);

    for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
      {
	if (fmt[i] == 'e')
	  mark_used_regs_combine (XEXP (x, i));
	else if (fmt[i] == 'E')
	  {
	    int j;

	    for (j = 0; j < XVECLEN (x, i); j++)
	      mark_used_regs_combine (XVECEXP (x, i, j));
	  }
      }
  }
}

/* Remove register number REGNO from the dead registers list of INSN.

   Return the note used to record the death, if there was one.  */

rtx
remove_death (unsigned int regno, rtx_insn *insn)
{
  rtx note = find_regno_note (insn, REG_DEAD, regno);

  if (note)
    remove_note (insn, note);

  return note;
}

/* For each register (hardware or pseudo) used within expression X, if its
   death is in an instruction with luid between FROM_LUID (inclusive) and
   TO_INSN (exclusive), put a REG_DEAD note for that register in the
   list headed by PNOTES.

   That said, don't move registers killed by maybe_kill_insn.

   This is done when X is being merged by combination into TO_INSN.  These
   notes will then be distributed as needed.  */

static void
move_deaths (rtx x, rtx maybe_kill_insn, int from_luid, rtx_insn *to_insn,
	     rtx *pnotes)
{
  const char *fmt;
  int len, i;
  enum rtx_code code = GET_CODE (x);

  if (code == REG)
    {
      unsigned int regno = REGNO (x);
      rtx_insn *where_dead = reg_stat[regno].last_death;

      /* If we do not know where the register died, it may still die between
	 FROM_LUID and TO_INSN.  If so, find it.  This is PR83304.  */
      if (!where_dead || DF_INSN_LUID (where_dead) >= DF_INSN_LUID (to_insn))
	{
	  rtx_insn *insn = prev_real_nondebug_insn (to_insn);
	  while (insn
		 && BLOCK_FOR_INSN (insn) == BLOCK_FOR_INSN (to_insn)
		 && DF_INSN_LUID (insn) >= from_luid)
	    {
	      if (dead_or_set_regno_p (insn, regno))
		{
		  if (find_regno_note (insn, REG_DEAD, regno))
		    where_dead = insn;
		  break;
		}

	      insn = prev_real_nondebug_insn (insn);
	    }
	}

      /* Don't move the register if it gets killed in between from and to.  */
      if (maybe_kill_insn && reg_set_p (x, maybe_kill_insn)
	  && ! reg_referenced_p (x, maybe_kill_insn))
	return;

      if (where_dead
	  && BLOCK_FOR_INSN (where_dead) == BLOCK_FOR_INSN (to_insn)
	  && DF_INSN_LUID (where_dead) >= from_luid
	  && DF_INSN_LUID (where_dead) < DF_INSN_LUID (to_insn))
	{
	  rtx note = remove_death (regno, where_dead);

	  /* It is possible for the call above to return 0.  This can occur
	     when last_death points to I2 or I1 that we combined with.
	     In that case make a new note.

	     We must also check for the case where X is a hard register
	     and NOTE is a death note for a range of hard registers
	     including X.  In that case, we must put REG_DEAD notes for
	     the remaining registers in place of NOTE.  */

	  if (note != 0 && regno < FIRST_PSEUDO_REGISTER
	      && partial_subreg_p (GET_MODE (x), GET_MODE (XEXP (note, 0))))
	    {
	      unsigned int deadregno = REGNO (XEXP (note, 0));
	      unsigned int deadend = END_REGNO (XEXP (note, 0));
	      unsigned int ourend = END_REGNO (x);
	      unsigned int i;

	      for (i = deadregno; i < deadend; i++)
		if (i < regno || i >= ourend)
		  add_reg_note (where_dead, REG_DEAD, regno_reg_rtx[i]);
	    }

	  /* If we didn't find any note, or if we found a REG_DEAD note that
	     covers only part of the given reg, and we have a multi-reg hard
	     register, then to be safe we must check for REG_DEAD notes
	     for each register other than the first.  They could have
	     their own REG_DEAD notes lying around.  */
	  else if ((note == 0
		    || (note != 0
			&& partial_subreg_p (GET_MODE (XEXP (note, 0)),
					     GET_MODE (x))))
		   && regno < FIRST_PSEUDO_REGISTER
		   && REG_NREGS (x) > 1)
	    {
	      unsigned int ourend = END_REGNO (x);
	      unsigned int i, offset;
	      rtx oldnotes = 0;

	      if (note)
		offset = hard_regno_nregs (regno, GET_MODE (XEXP (note, 0)));
	      else
		offset = 1;

	      for (i = regno + offset; i < ourend; i++)
		move_deaths (regno_reg_rtx[i],
			     maybe_kill_insn, from_luid, to_insn, &oldnotes);
	    }

	  if (note != 0 && GET_MODE (XEXP (note, 0)) == GET_MODE (x))
	    {
	      XEXP (note, 1) = *pnotes;
	      *pnotes = note;
	    }
	  else
	    *pnotes = alloc_reg_note (REG_DEAD, x, *pnotes);
	}

      return;
    }

  else if (GET_CODE (x) == SET)
    {
      rtx dest = SET_DEST (x);

      move_deaths (SET_SRC (x), maybe_kill_insn, from_luid, to_insn, pnotes);

      /* In the case of a ZERO_EXTRACT, a STRICT_LOW_PART, or a SUBREG
	 that accesses one word of a multi-word item, some
	 piece of everything register in the expression is used by
	 this insn, so remove any old death.  */
      /* ??? So why do we test for equality of the sizes?  */

      if (GET_CODE (dest) == ZERO_EXTRACT
	  || GET_CODE (dest) == STRICT_LOW_PART
	  || (GET_CODE (dest) == SUBREG
	      && !read_modify_subreg_p (dest)))
	{
	  move_deaths (dest, maybe_kill_insn, from_luid, to_insn, pnotes);
	  return;
	}

      /* If this is some other SUBREG, we know it replaces the entire
	 value, so use that as the destination.  */
      if (GET_CODE (dest) == SUBREG)
	dest = SUBREG_REG (dest);

      /* If this is a MEM, adjust deaths of anything used in the address.
	 For a REG (the only other possibility), the entire value is
	 being replaced so the old value is not used in this insn.  */

      if (MEM_P (dest))
	move_deaths (XEXP (dest, 0), maybe_kill_insn, from_luid,
		     to_insn, pnotes);
      return;
    }

  else if (GET_CODE (x) == CLOBBER)
    return;

  len = GET_RTX_LENGTH (code);
  fmt = GET_RTX_FORMAT (code);

  for (i = 0; i < len; i++)
    {
      if (fmt[i] == 'E')
	{
	  int j;
	  for (j = XVECLEN (x, i) - 1; j >= 0; j--)
	    move_deaths (XVECEXP (x, i, j), maybe_kill_insn, from_luid,
			 to_insn, pnotes);
	}
      else if (fmt[i] == 'e')
	move_deaths (XEXP (x, i), maybe_kill_insn, from_luid, to_insn, pnotes);
    }
}

/* Return 1 if X is the target of a bit-field assignment in BODY, the
   pattern of an insn.  X must be a REG.  */

static int
reg_bitfield_target_p (rtx x, rtx body)
{
  int i;

  if (GET_CODE (body) == SET)
    {
      rtx dest = SET_DEST (body);
      rtx target;
      unsigned int regno, tregno, endregno, endtregno;

      if (GET_CODE (dest) == ZERO_EXTRACT)
	target = XEXP (dest, 0);
      else if (GET_CODE (dest) == STRICT_LOW_PART)
	target = SUBREG_REG (XEXP (dest, 0));
      else
	return 0;

      if (GET_CODE (target) == SUBREG)
	target = SUBREG_REG (target);

      if (!REG_P (target))
	return 0;

      tregno = REGNO (target), regno = REGNO (x);
      if (tregno >= FIRST_PSEUDO_REGISTER || regno >= FIRST_PSEUDO_REGISTER)
	return target == x;

      endtregno = end_hard_regno (GET_MODE (target), tregno);
      endregno = end_hard_regno (GET_MODE (x), regno);

      return endregno > tregno && regno < endtregno;
    }

  else if (GET_CODE (body) == PARALLEL)
    for (i = XVECLEN (body, 0) - 1; i >= 0; i--)
      if (reg_bitfield_target_p (x, XVECEXP (body, 0, i)))
	return 1;

  return 0;
}

/* Given a chain of REG_NOTES originally from FROM_INSN, try to place them
   as appropriate.  I3 and I2 are the insns resulting from the combination
   insns including FROM (I2 may be zero).

   ELIM_I2 and ELIM_I1 are either zero or registers that we know will
   not need REG_DEAD notes because they are being substituted for.  This
   saves searching in the most common cases.

   Each note in the list is either ignored or placed on some insns, depending
   on the type of note.  */

static void
distribute_notes (rtx notes, rtx_insn *from_insn, rtx_insn *i3, rtx_insn *i2,
		  rtx elim_i2, rtx elim_i1, rtx elim_i0)
{
  rtx note, next_note;
  rtx tem_note;
  rtx_insn *tem_insn;

  for (note = notes; note; note = next_note)
    {
      rtx_insn *place = 0, *place2 = 0;

      next_note = XEXP (note, 1);
      switch (REG_NOTE_KIND (note))
	{
	case REG_BR_PROB:
	case REG_BR_PRED:
	  /* Doesn't matter much where we put this, as long as it's somewhere.
	     It is preferable to keep these notes on branches, which is most
	     likely to be i3.  */
	  place = i3;
	  break;

	case REG_NON_LOCAL_GOTO:
	  if (JUMP_P (i3))
	    place = i3;
	  else
	    {
	      gcc_assert (i2 && JUMP_P (i2));
	      place = i2;
	    }
	  break;

	case REG_EH_REGION:
	  /* These notes must remain with the call or trapping instruction.  */
	  if (CALL_P (i3))
	    place = i3;
	  else if (i2 && CALL_P (i2))
	    place = i2;
	  else
	    {
	      gcc_assert (cfun->can_throw_non_call_exceptions);
	      if (may_trap_p (i3))
		place = i3;
	      else if (i2 && may_trap_p (i2))
		place = i2;
	      /* ??? Otherwise assume we've combined things such that we
		 can now prove that the instructions can't trap.  Drop the
		 note in this case.  */
	    }
	  break;

	case REG_ARGS_SIZE:
	  /* ??? How to distribute between i3-i1.  Assume i3 contains the
	     entire adjustment.  Assert i3 contains at least some adjust.  */
	  if (!noop_move_p (i3))
	    {
	      poly_int64 old_size, args_size = get_args_size (note);
	      /* fixup_args_size_notes looks at REG_NORETURN note,
		 so ensure the note is placed there first.  */
	      if (CALL_P (i3))
		{
		  rtx *np;
		  for (np = &next_note; *np; np = &XEXP (*np, 1))
		    if (REG_NOTE_KIND (*np) == REG_NORETURN)
		      {
			rtx n = *np;
			*np = XEXP (n, 1);
			XEXP (n, 1) = REG_NOTES (i3);
			REG_NOTES (i3) = n;
			break;
		      }
		}
	      old_size = fixup_args_size_notes (PREV_INSN (i3), i3, args_size);
	      /* emit_call_1 adds for !ACCUMULATE_OUTGOING_ARGS
		 REG_ARGS_SIZE note to all noreturn calls, allow that here.  */
	      gcc_assert (maybe_ne (old_size, args_size)
			  || (CALL_P (i3)
			      && !ACCUMULATE_OUTGOING_ARGS
			      && find_reg_note (i3, REG_NORETURN, NULL_RTX)));
	    }
	  break;

	case REG_NORETURN:
	case REG_SETJMP:
	case REG_TM:
	case REG_CALL_DECL:
	case REG_CALL_NOCF_CHECK:
	  /* These notes must remain with the call.  It should not be
	     possible for both I2 and I3 to be a call.  */
	  if (CALL_P (i3))
	    place = i3;
	  else
	    {
	      gcc_assert (i2 && CALL_P (i2));
	      place = i2;
	    }
	  break;

	case REG_UNUSED:
	  /* Any clobbers for i3 may still exist, and so we must process
	     REG_UNUSED notes from that insn.

	     Any clobbers from i2 or i1 can only exist if they were added by
	     recog_for_combine.  In that case, recog_for_combine created the
	     necessary REG_UNUSED notes.  Trying to keep any original
	     REG_UNUSED notes from these insns can cause incorrect output
	     if it is for the same register as the original i3 dest.
	     In that case, we will notice that the register is set in i3,
	     and then add a REG_UNUSED note for the destination of i3, which
	     is wrong.  However, it is possible to have REG_UNUSED notes from
	     i2 or i1 for register which were both used and clobbered, so
	     we keep notes from i2 or i1 if they will turn into REG_DEAD
	     notes.  */

	  /* If this register is set or clobbered in I3, put the note there
	     unless there is one already.  */
	  if (reg_set_p (XEXP (note, 0), PATTERN (i3)))
	    {
	      if (from_insn != i3)
		break;

	      if (! (REG_P (XEXP (note, 0))
		     ? find_regno_note (i3, REG_UNUSED, REGNO (XEXP (note, 0)))
		     : find_reg_note (i3, REG_UNUSED, XEXP (note, 0))))
		place = i3;
	    }
	  /* Otherwise, if this register is used by I3, then this register
	     now dies here, so we must put a REG_DEAD note here unless there
	     is one already.  */
	  else if (reg_referenced_p (XEXP (note, 0), PATTERN (i3))
		   && ! (REG_P (XEXP (note, 0))
			 ? find_regno_note (i3, REG_DEAD,
					    REGNO (XEXP (note, 0)))
			 : find_reg_note (i3, REG_DEAD, XEXP (note, 0))))
	    {
	      PUT_REG_NOTE_KIND (note, REG_DEAD);
	      place = i3;
	    }

	  /* A SET or CLOBBER of the REG_UNUSED reg has been removed,
	     but we can't tell which at this point.  We must reset any
	     expectations we had about the value that was previously
	     stored in the reg.  ??? Ideally, we'd adjust REG_N_SETS
	     and, if appropriate, restore its previous value, but we
	     don't have enough information for that at this point.  */
	  else
	    {
	      record_value_for_reg (XEXP (note, 0), NULL, NULL_RTX);

	      /* Otherwise, if this register is now referenced in i2
		 then the register used to be modified in one of the
		 original insns.  If it was i3 (say, in an unused
		 parallel), it's now completely gone, so the note can
		 be discarded.  But if it was modified in i2, i1 or i0
		 and we still reference it in i2, then we're
		 referencing the previous value, and since the
		 register was modified and REG_UNUSED, we know that
		 the previous value is now dead.  So, if we only
		 reference the register in i2, we change the note to
		 REG_DEAD, to reflect the previous value.  However, if
		 we're also setting or clobbering the register as
		 scratch, we know (because the register was not
		 referenced in i3) that it's unused, just as it was
		 unused before, and we place the note in i2.  */
	      if (from_insn != i3 && i2 && INSN_P (i2)
		  && reg_referenced_p (XEXP (note, 0), PATTERN (i2)))
		{
		  if (!reg_set_p (XEXP (note, 0), PATTERN (i2)))
		    PUT_REG_NOTE_KIND (note, REG_DEAD);
		  if (! (REG_P (XEXP (note, 0))
			 ? find_regno_note (i2, REG_NOTE_KIND (note),
					    REGNO (XEXP (note, 0)))
			 : find_reg_note (i2, REG_NOTE_KIND (note),
					  XEXP (note, 0))))
		    place = i2;
		}
	    }

	  break;

	case REG_EQUAL:
	case REG_EQUIV:
	case REG_NOALIAS:
	  /* These notes say something about results of an insn.  We can
	     only support them if they used to be on I3 in which case they
	     remain on I3.  Otherwise they are ignored.

	     If the note refers to an expression that is not a constant, we
	     must also ignore the note since we cannot tell whether the
	     equivalence is still true.  It might be possible to do
	     slightly better than this (we only have a problem if I2DEST
	     or I1DEST is present in the expression), but it doesn't
	     seem worth the trouble.  */

	  if (from_insn == i3
	      && (XEXP (note, 0) == 0 || CONSTANT_P (XEXP (note, 0))))
	    place = i3;
	  break;

	case REG_INC:
	  /* These notes say something about how a register is used.  They must
	     be present on any use of the register in I2 or I3.  */
	  if (reg_mentioned_p (XEXP (note, 0), PATTERN (i3)))
	    place = i3;

	  if (i2 && reg_mentioned_p (XEXP (note, 0), PATTERN (i2)))
	    {
	      if (place)
		place2 = i2;
	      else
		place = i2;
	    }
	  break;

	case REG_LABEL_TARGET:
	case REG_LABEL_OPERAND:
	  /* This can show up in several ways -- either directly in the
	     pattern, or hidden off in the constant pool with (or without?)
	     a REG_EQUAL note.  */
	  /* ??? Ignore the without-reg_equal-note problem for now.  */
	  if (reg_mentioned_p (XEXP (note, 0), PATTERN (i3))
	      || ((tem_note = find_reg_note (i3, REG_EQUAL, NULL_RTX))
		  && GET_CODE (XEXP (tem_note, 0)) == LABEL_REF
		  && label_ref_label (XEXP (tem_note, 0)) == XEXP (note, 0)))
	    place = i3;

	  if (i2
	      && (reg_mentioned_p (XEXP (note, 0), PATTERN (i2))
		  || ((tem_note = find_reg_note (i2, REG_EQUAL, NULL_RTX))
		      && GET_CODE (XEXP (tem_note, 0)) == LABEL_REF
		      && label_ref_label (XEXP (tem_note, 0)) == XEXP (note, 0))))
	    {
	      if (place)
		place2 = i2;
	      else
		place = i2;
	    }

	  /* For REG_LABEL_TARGET on a JUMP_P, we prefer to put the note
	     as a JUMP_LABEL or decrement LABEL_NUSES if it's already
	     there.  */
	  if (place && JUMP_P (place)
	      && REG_NOTE_KIND (note) == REG_LABEL_TARGET
	      && (JUMP_LABEL (place) == NULL
		  || JUMP_LABEL (place) == XEXP (note, 0)))
	    {
	      rtx label = JUMP_LABEL (place);

	      if (!label)
		JUMP_LABEL (place) = XEXP (note, 0);
	      else if (LABEL_P (label))
		LABEL_NUSES (label)--;
	    }

	  if (place2 && JUMP_P (place2)
	      && REG_NOTE_KIND (note) == REG_LABEL_TARGET
	      && (JUMP_LABEL (place2) == NULL
		  || JUMP_LABEL (place2) == XEXP (note, 0)))
	    {
	      rtx label = JUMP_LABEL (place2);

	      if (!label)
		JUMP_LABEL (place2) = XEXP (note, 0);
	      else if (LABEL_P (label))
		LABEL_NUSES (label)--;
	      place2 = 0;
	    }
	  break;

	case REG_NONNEG:
	  /* This note says something about the value of a register prior
	     to the execution of an insn.  It is too much trouble to see
	     if the note is still correct in all situations.  It is better
	     to simply delete it.  */
	  break;

	case REG_DEAD:
	  /* If we replaced the right hand side of FROM_INSN with a
	     REG_EQUAL note, the original use of the dying register
	     will not have been combined into I3 and I2.  In such cases,
	     FROM_INSN is guaranteed to be the first of the combined
	     instructions, so we simply need to search back before
	     FROM_INSN for the previous use or set of this register,
	     then alter the notes there appropriately.

	     If the register is used as an input in I3, it dies there.
	     Similarly for I2, if it is nonzero and adjacent to I3.

	     If the register is not used as an input in either I3 or I2
	     and it is not one of the registers we were supposed to eliminate,
	     there are two possibilities.  We might have a non-adjacent I2
	     or we might have somehow eliminated an additional register
	     from a computation.  For example, we might have had A & B where
	     we discover that B will always be zero.  In this case we will
	     eliminate the reference to A.

	     In both cases, we must search to see if we can find a previous
	     use of A and put the death note there.  */

	  if (from_insn
	      && from_insn == i2mod
	      && !reg_overlap_mentioned_p (XEXP (note, 0), i2mod_new_rhs))
	    tem_insn = from_insn;
	  else
	    {
	      if (from_insn
		  && CALL_P (from_insn)
		  && find_reg_fusage (from_insn, USE, XEXP (note, 0)))
		place = from_insn;
	      else if (i2 && reg_set_p (XEXP (note, 0), PATTERN (i2)))
		{
		  /* If the new I2 sets the same register that is marked
		     dead in the note, we do not in general know where to
		     put the note.  One important case we _can_ handle is
		     when the note comes from I3.  */
		  if (from_insn == i3)
		    place = i3;
		  else
		    break;
		}
	      else if (reg_referenced_p (XEXP (note, 0), PATTERN (i3)))
		place = i3;
	      else if (i2 != 0 && next_nonnote_nondebug_insn (i2) == i3
		       && reg_referenced_p (XEXP (note, 0), PATTERN (i2)))
		place = i2;
	      else if ((rtx_equal_p (XEXP (note, 0), elim_i2)
			&& !(i2mod
			     && reg_overlap_mentioned_p (XEXP (note, 0),
							 i2mod_old_rhs)))
		       || rtx_equal_p (XEXP (note, 0), elim_i1)
		       || rtx_equal_p (XEXP (note, 0), elim_i0))
		break;
	      tem_insn = i3;
	    }

	  if (place == 0)
	    {
	      basic_block bb = this_basic_block;

	      for (tem_insn = PREV_INSN (tem_insn); place == 0; tem_insn = PREV_INSN (tem_insn))
		{
		  if (!NONDEBUG_INSN_P (tem_insn))
		    {
		      if (tem_insn == BB_HEAD (bb))
			break;
		      continue;
		    }

		  /* If the register is being set at TEM_INSN, see if that is all
		     TEM_INSN is doing.  If so, delete TEM_INSN.  Otherwise, make this
		     into a REG_UNUSED note instead. Don't delete sets to
		     global register vars.  */
		  if ((REGNO (XEXP (note, 0)) >= FIRST_PSEUDO_REGISTER
		       || !global_regs[REGNO (XEXP (note, 0))])
		      && reg_set_p (XEXP (note, 0), PATTERN (tem_insn)))
		    {
		      rtx set = single_set (tem_insn);
		      rtx inner_dest = 0;
		      rtx_insn *cc0_setter = NULL;

		      if (set != 0)
			for (inner_dest = SET_DEST (set);
			     (GET_CODE (inner_dest) == STRICT_LOW_PART
			      || GET_CODE (inner_dest) == SUBREG
			      || GET_CODE (inner_dest) == ZERO_EXTRACT);
			     inner_dest = XEXP (inner_dest, 0))
			  ;

		      /* Verify that it was the set, and not a clobber that
			 modified the register.

			 CC0 targets must be careful to maintain setter/user
			 pairs.  If we cannot delete the setter due to side
			 effects, mark the user with an UNUSED note instead
			 of deleting it.  */

		      if (set != 0 && ! side_effects_p (SET_SRC (set))
			  && rtx_equal_p (XEXP (note, 0), inner_dest)
			  && (!HAVE_cc0
			      || (! reg_mentioned_p (cc0_rtx, SET_SRC (set))
				  || ((cc0_setter = prev_cc0_setter (tem_insn)) != NULL
				      && sets_cc0_p (PATTERN (cc0_setter)) > 0))))
			{
			  /* Move the notes and links of TEM_INSN elsewhere.
			     This might delete other dead insns recursively.
			     First set the pattern to something that won't use
			     any register.  */
			  rtx old_notes = REG_NOTES (tem_insn);

			  PATTERN (tem_insn) = pc_rtx;
			  REG_NOTES (tem_insn) = NULL;

			  distribute_notes (old_notes, tem_insn, tem_insn, NULL,
					    NULL_RTX, NULL_RTX, NULL_RTX);
			  distribute_links (LOG_LINKS (tem_insn));

			  unsigned int regno = REGNO (XEXP (note, 0));
			  reg_stat_type *rsp = &reg_stat[regno];
			  if (rsp->last_set == tem_insn)
			    record_value_for_reg (XEXP (note, 0), NULL, NULL_RTX);

			  SET_INSN_DELETED (tem_insn);
			  if (tem_insn == i2)
			    i2 = NULL;

			  /* Delete the setter too.  */
			  if (cc0_setter)
			    {
			      PATTERN (cc0_setter) = pc_rtx;
			      old_notes = REG_NOTES (cc0_setter);
			      REG_NOTES (cc0_setter) = NULL;

			      distribute_notes (old_notes, cc0_setter,
						cc0_setter, NULL,
						NULL_RTX, NULL_RTX, NULL_RTX);
			      distribute_links (LOG_LINKS (cc0_setter));

			      SET_INSN_DELETED (cc0_setter);
			      if (cc0_setter == i2)
				i2 = NULL;
			    }
			}
		      else
			{
			  PUT_REG_NOTE_KIND (note, REG_UNUSED);

			  /*  If there isn't already a REG_UNUSED note, put one
			      here.  Do not place a REG_DEAD note, even if
			      the register is also used here; that would not
			      match the algorithm used in lifetime analysis
			      and can cause the consistency check in the
			      scheduler to fail.  */
			  if (! find_regno_note (tem_insn, REG_UNUSED,
						 REGNO (XEXP (note, 0))))
			    place = tem_insn;
			  break;
			}
		    }
		  else if (reg_referenced_p (XEXP (note, 0), PATTERN (tem_insn))
			   || (CALL_P (tem_insn)
			       && find_reg_fusage (tem_insn, USE, XEXP (note, 0))))
		    {
		      place = tem_insn;

		      /* If we are doing a 3->2 combination, and we have a
			 register which formerly died in i3 and was not used
			 by i2, which now no longer dies in i3 and is used in
			 i2 but does not die in i2, and place is between i2
			 and i3, then we may need to move a link from place to
			 i2.  */
		      if (i2 && DF_INSN_LUID (place) > DF_INSN_LUID (i2)
			  && from_insn
			  && DF_INSN_LUID (from_insn) > DF_INSN_LUID (i2)
			  && reg_referenced_p (XEXP (note, 0), PATTERN (i2)))
			{
			  struct insn_link *links = LOG_LINKS (place);
			  LOG_LINKS (place) = NULL;
			  distribute_links (links);
			}
		      break;
		    }

		  if (tem_insn == BB_HEAD (bb))
		    break;
		}

	    }

	  /* If the register is set or already dead at PLACE, we needn't do
	     anything with this note if it is still a REG_DEAD note.
	     We check here if it is set at all, not if is it totally replaced,
	     which is what `dead_or_set_p' checks, so also check for it being
	     set partially.  */

	  if (place && REG_NOTE_KIND (note) == REG_DEAD)
	    {
	      unsigned int regno = REGNO (XEXP (note, 0));
	      reg_stat_type *rsp = &reg_stat[regno];

	      if (dead_or_set_p (place, XEXP (note, 0))
		  || reg_bitfield_target_p (XEXP (note, 0), PATTERN (place)))
		{
		  /* Unless the register previously died in PLACE, clear
		     last_death.  [I no longer understand why this is
		     being done.] */
		  if (rsp->last_death != place)
		    rsp->last_death = 0;
		  place = 0;
		}
	      else
		rsp->last_death = place;

	      /* If this is a death note for a hard reg that is occupying
		 multiple registers, ensure that we are still using all
		 parts of the object.  If we find a piece of the object
		 that is unused, we must arrange for an appropriate REG_DEAD
		 note to be added for it.  However, we can't just emit a USE
		 and tag the note to it, since the register might actually
		 be dead; so we recourse, and the recursive call then finds
		 the previous insn that used this register.  */

	      if (place && REG_NREGS (XEXP (note, 0)) > 1)
		{
		  unsigned int endregno = END_REGNO (XEXP (note, 0));
		  bool all_used = true;
		  unsigned int i;

		  for (i = regno; i < endregno; i++)
		    if ((! refers_to_regno_p (i, PATTERN (place))
			 && ! find_regno_fusage (place, USE, i))
			|| dead_or_set_regno_p (place, i))
		      {
			all_used = false;
			break;
		      }

		  if (! all_used)
		    {
		      /* Put only REG_DEAD notes for pieces that are
			 not already dead or set.  */

		      for (i = regno; i < endregno;
			   i += hard_regno_nregs (i, reg_raw_mode[i]))
			{
			  rtx piece = regno_reg_rtx[i];
			  basic_block bb = this_basic_block;

			  if (! dead_or_set_p (place, piece)
			      && ! reg_bitfield_target_p (piece,
							  PATTERN (place)))
			    {
			      rtx new_note = alloc_reg_note (REG_DEAD, piece,
							     NULL_RTX);

			      distribute_notes (new_note, place, place,
						NULL, NULL_RTX, NULL_RTX,
						NULL_RTX);
			    }
			  else if (! refers_to_regno_p (i, PATTERN (place))
				   && ! find_regno_fusage (place, USE, i))
			    for (tem_insn = PREV_INSN (place); ;
				 tem_insn = PREV_INSN (tem_insn))
			      {
				if (!NONDEBUG_INSN_P (tem_insn))
				  {
				    if (tem_insn == BB_HEAD (bb))
			 	      break;
				    continue;
				  }
				if (dead_or_set_p (tem_insn, piece)
				    || reg_bitfield_target_p (piece,
							      PATTERN (tem_insn)))
				  {
				    add_reg_note (tem_insn, REG_UNUSED, piece);
				    break;
				  }
			      }
			}

		      place = 0;
		    }
		}
	    }
	  break;

	default:
	  /* Any other notes should not be present at this point in the
	     compilation.  */
	  gcc_unreachable ();
	}

      if (place)
	{
	  XEXP (note, 1) = REG_NOTES (place);
	  REG_NOTES (place) = note;

	  /* Set added_notes_insn to the earliest insn we added a note to.  */
	  if (added_notes_insn == 0
	      || DF_INSN_LUID (added_notes_insn) > DF_INSN_LUID (place))
	    added_notes_insn = place;
	}

      if (place2)
	{
	  add_shallow_copy_of_reg_note (place2, note);

	  /* Set added_notes_insn to the earliest insn we added a note to.  */
	  if (added_notes_insn == 0
	      || DF_INSN_LUID (added_notes_insn) > DF_INSN_LUID (place2))
	    added_notes_insn = place2;
	}
    }
}

/* Similarly to above, distribute the LOG_LINKS that used to be present on
   I3, I2, and I1 to new locations.  This is also called to add a link
   pointing at I3 when I3's destination is changed.  */

static void
distribute_links (struct insn_link *links)
{
  struct insn_link *link, *next_link;

  for (link = links; link; link = next_link)
    {
      rtx_insn *place = 0;
      rtx_insn *insn;
      rtx set, reg;

      next_link = link->next;

      /* If the insn that this link points to is a NOTE, ignore it.  */
      if (NOTE_P (link->insn))
	continue;

      set = 0;
      rtx pat = PATTERN (link->insn);
      if (GET_CODE (pat) == SET)
	set = pat;
      else if (GET_CODE (pat) == PARALLEL)
	{
	  int i;
	  for (i = 0; i < XVECLEN (pat, 0); i++)
	    {
	      set = XVECEXP (pat, 0, i);
	      if (GET_CODE (set) != SET)
		continue;

	      reg = SET_DEST (set);
	      while (GET_CODE (reg) == ZERO_EXTRACT
		     || GET_CODE (reg) == STRICT_LOW_PART
		     || GET_CODE (reg) == SUBREG)
		reg = XEXP (reg, 0);

	      if (!REG_P (reg))
		continue;

	      if (REGNO (reg) == link->regno)
		break;
	    }
	  if (i == XVECLEN (pat, 0))
	    continue;
	}
      else
	continue;

      reg = SET_DEST (set);

      while (GET_CODE (reg) == ZERO_EXTRACT
	     || GET_CODE (reg) == STRICT_LOW_PART
	     || GET_CODE (reg) == SUBREG)
	reg = XEXP (reg, 0);

      if (reg == pc_rtx)
	continue;

      /* A LOG_LINK is defined as being placed on the first insn that uses
	 a register and points to the insn that sets the register.  Start
	 searching at the next insn after the target of the link and stop
	 when we reach a set of the register or the end of the basic block.

	 Note that this correctly handles the link that used to point from
	 I3 to I2.  Also note that not much searching is typically done here
	 since most links don't point very far away.  */

      for (insn = NEXT_INSN (link->insn);
	   (insn && (this_basic_block->next_bb == EXIT_BLOCK_PTR_FOR_FN (cfun)
		     || BB_HEAD (this_basic_block->next_bb) != insn));
	   insn = NEXT_INSN (insn))
	if (DEBUG_INSN_P (insn))
	  continue;
	else if (INSN_P (insn) && reg_overlap_mentioned_p (reg, PATTERN (insn)))
	  {
	    if (reg_referenced_p (reg, PATTERN (insn)))
	      place = insn;
	    break;
	  }
	else if (CALL_P (insn)
		 && find_reg_fusage (insn, USE, reg))
	  {
	    place = insn;
	    break;
	  }
	else if (INSN_P (insn) && reg_set_p (reg, insn))
	  break;

      /* If we found a place to put the link, place it there unless there
	 is already a link to the same insn as LINK at that point.  */

      if (place)
	{
	  struct insn_link *link2;

	  FOR_EACH_LOG_LINK (link2, place)
	    if (link2->insn == link->insn && link2->regno == link->regno)
	      break;

	  if (link2 == NULL)
	    {
	      link->next = LOG_LINKS (place);
	      LOG_LINKS (place) = link;

	      /* Set added_links_insn to the earliest insn we added a
		 link to.  */
	      if (added_links_insn == 0
		  || DF_INSN_LUID (added_links_insn) > DF_INSN_LUID (place))
		added_links_insn = place;
	    }
	}
    }
}

/* Check for any register or memory mentioned in EQUIV that is not
   mentioned in EXPR.  This is used to restrict EQUIV to "specializations"
   of EXPR where some registers may have been replaced by constants.  */

static bool
unmentioned_reg_p (rtx equiv, rtx expr)
{
  subrtx_iterator::array_type array;
  FOR_EACH_SUBRTX (iter, array, equiv, NONCONST)
    {
      const_rtx x = *iter;
      if ((REG_P (x) || MEM_P (x))
	  && !reg_mentioned_p (x, expr))
	return true;
    }
  return false;
}

DEBUG_FUNCTION void
dump_combine_stats (FILE *file)
{
  fprintf
    (file,
     ";; Combiner statistics: %d attempts, %d substitutions (%d requiring new space),\n;; %d successes.\n\n",
     combine_attempts, combine_merges, combine_extras, combine_successes);
}

void
dump_combine_total_stats (FILE *file)
{
  fprintf
    (file,
     "\n;; Combiner totals: %d attempts, %d substitutions (%d requiring new space),\n;; %d successes.\n",
     total_attempts, total_merges, total_extras, total_successes);
}

/* Make pseudo-to-pseudo copies after every hard-reg-to-pseudo-copy, because
   the reg-to-reg copy can usefully combine with later instructions, but we
   do not want to combine the hard reg into later instructions, for that
   restricts register allocation.  */
static void
make_more_copies (void)
{
  basic_block bb;

  FOR_EACH_BB_FN (bb, cfun)
    {
      rtx_insn *insn;

      FOR_BB_INSNS (bb, insn)
        {
          if (!NONDEBUG_INSN_P (insn))
            continue;

	  rtx set = single_set (insn);
	  if (!set)
	    continue;
	  rtx dest = SET_DEST (set);
	  if (dest == pc_rtx)
	    continue;
	  /* See PR87871.  */
	  if (dest == frame_pointer_rtx)
	    continue;
	  rtx src = SET_SRC (set);
	  if (!(REG_P (src) && HARD_REGISTER_P (src)))
	    continue;
	  if (TEST_HARD_REG_BIT (fixed_reg_set, REGNO (src)))
	    continue;

	  rtx new_reg = gen_reg_rtx (GET_MODE (dest));
	  rtx_insn *new_insn = gen_move_insn (new_reg, src);
	  SET_SRC (set) = new_reg;
	  emit_insn_before (new_insn, insn);
	  df_insn_rescan (insn);
	}
    }
}

/* Try combining insns through substitution.  */
static unsigned int
rest_of_handle_combine (void)
{
  make_more_copies ();

  df_set_flags (DF_LR_RUN_DCE + DF_DEFER_INSN_RESCAN);
  df_note_add_problem ();
  df_analyze ();

  regstat_init_n_sets_and_refs ();
  reg_n_sets_max = max_reg_num ();

  int rebuild_jump_labels_after_combine
    = combine_instructions (get_insns (), max_reg_num ());

  /* Combining insns may have turned an indirect jump into a
     direct jump.  Rebuild the JUMP_LABEL fields of jumping
     instructions.  */
  if (rebuild_jump_labels_after_combine)
    {
      if (dom_info_available_p (CDI_DOMINATORS))
	free_dominance_info (CDI_DOMINATORS);
      timevar_push (TV_JUMP);
      rebuild_jump_labels (get_insns ());
      cleanup_cfg (0);
      timevar_pop (TV_JUMP);
    }

  regstat_free_n_sets_and_refs ();
  return 0;
}

namespace {

const pass_data pass_data_combine =
{
  RTL_PASS, /* type */
  "combine", /* name */
  OPTGROUP_NONE, /* optinfo_flags */
  TV_COMBINE, /* tv_id */
  PROP_cfglayout, /* properties_required */
  0, /* properties_provided */
  0, /* properties_destroyed */
  0, /* todo_flags_start */
  TODO_df_finish, /* todo_flags_finish */
};

class pass_combine : public rtl_opt_pass
{
public:
  pass_combine (gcc::context *ctxt)
    : rtl_opt_pass (pass_data_combine, ctxt)
  {}

  /* opt_pass methods: */
  virtual bool gate (function *) { return (optimize > 0); }
  virtual unsigned int execute (function *)
    {
      return rest_of_handle_combine ();
    }

}; // class pass_combine

} // anon namespace

rtl_opt_pass *
make_pass_combine (gcc::context *ctxt)
{
  return new pass_combine (ctxt);
}
