/* Common subexpression elimination for GNU compiler.
   Copyright (C) 1987, 1988, 1989, 1992, 1993, 1994, 1995, 1996, 1997, 1998
   1999, 2000, 2001, 2002, 2004 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 2, or (at your option) any later
version.

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

You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING.  If not, write to the Free
Software Foundation, 59 Temple Place - Suite 330, Boston, MA
02111-1307, USA.  */

#include "config.h"
/* stdio.h must precede rtl.h for FFS.  */
#include "system.h"

#include "rtl.h"
#include "tm_p.h"
#include "regs.h"
#include "hard-reg-set.h"
#include "basic-block.h"
#include "flags.h"
#include "real.h"
#include "insn-config.h"
#include "recog.h"
#include "function.h"
#include "expr.h"
#include "toplev.h"
#include "output.h"
#include "ggc.h"
#include "timevar.h"
#include "target.h"

/* The basic idea of common subexpression elimination is to go
   through the code, keeping a record of expressions that would
   have the same value at the current scan point, and replacing
   expressions encountered with the cheapest equivalent expression.

   It is too complicated to keep track of the different possibilities
   when control paths merge in this code; so, at each label, we forget all
   that is known and start fresh.  This can be described as processing each
   extended basic block separately.  We have a separate pass to perform
   global CSE.

   Note CSE can turn a conditional or computed jump into a nop or
   an unconditional jump.  When this occurs we arrange to run the jump
   optimizer after CSE to delete the unreachable code.

   We use two data structures to record the equivalent expressions:
   a hash table for most expressions, and a vector of "quantity
   numbers" to record equivalent (pseudo) registers.

   The use of the special data structure for registers is desirable
   because it is faster.  It is possible because registers references
   contain a fairly small number, the register number, taken from
   a contiguously allocated series, and two register references are
   identical if they have the same number.  General expressions
   do not have any such thing, so the only way to retrieve the
   information recorded on an expression other than a register
   is to keep it in a hash table.

Registers and "quantity numbers":

   At the start of each basic block, all of the (hardware and pseudo)
   registers used in the function are given distinct quantity
   numbers to indicate their contents.  During scan, when the code
   copies one register into another, we copy the quantity number.
   When a register is loaded in any other way, we allocate a new
   quantity number to describe the value generated by this operation.
   `reg_qty' records what quantity a register is currently thought
   of as containing.

   All real quantity numbers are greater than or equal to `max_reg'.
   If register N has not been assigned a quantity, reg_qty[N] will equal N.

   Quantity numbers below `max_reg' do not exist and none of the `qty_table'
   entries should be referenced with an index below `max_reg'.

   We also maintain a bidirectional chain of registers for each
   quantity number.  The `qty_table` members `first_reg' and `last_reg',
   and `reg_eqv_table' members `next' and `prev' hold these chains.

   The first register in a chain is the one whose lifespan is least local.
   Among equals, it is the one that was seen first.
   We replace any equivalent register with that one.

   If two registers have the same quantity number, it must be true that
   REG expressions with qty_table `mode' must be in the hash table for both
   registers and must be in the same class.

   The converse is not true.  Since hard registers may be referenced in
   any mode, two REG expressions might be equivalent in the hash table
   but not have the same quantity number if the quantity number of one
   of the registers is not the same mode as those expressions.

Constants and quantity numbers

   When a quantity has a known constant value, that value is stored
   in the appropriate qty_table `const_rtx'.  This is in addition to
   putting the constant in the hash table as is usual for non-regs.

   Whether a reg or a constant is preferred is determined by the configuration
   macro CONST_COSTS and will often depend on the constant value.  In any
   event, expressions containing constants can be simplified, by fold_rtx.

   When a quantity has a known nearly constant value (such as an address
   of a stack slot), that value is stored in the appropriate qty_table
   `const_rtx'.

   Integer constants don't have a machine mode.  However, cse
   determines the intended machine mode from the destination
   of the instruction that moves the constant.  The machine mode
   is recorded in the hash table along with the actual RTL
   constant expression so that different modes are kept separate.

Other expressions:

   To record known equivalences among expressions in general
   we use a hash table called `table'.  It has a fixed number of buckets
   that contain chains of `struct table_elt' elements for expressions.
   These chains connect the elements whose expressions have the same
   hash codes.

   Other chains through the same elements connect the elements which
   currently have equivalent values.

   Register references in an expression are canonicalized before hashing
   the expression.  This is done using `reg_qty' and qty_table `first_reg'.
   The hash code of a register reference is computed using the quantity
   number, not the register number.

   When the value of an expression changes, it is necessary to remove from the
   hash table not just that expression but all expressions whose values
   could be different as a result.

     1. If the value changing is in memory, except in special cases
     ANYTHING referring to memory could be changed.  That is because
     nobody knows where a pointer does not point.
     The function `invalidate_memory' removes what is necessary.

     The special cases are when the address is constant or is
     a constant plus a fixed register such as the frame pointer
     or a static chain pointer.  When such addresses are stored in,
     we can tell exactly which other such addresses must be invalidated
     due to overlap.  `invalidate' does this.
     All expressions that refer to non-constant
     memory addresses are also invalidated.  `invalidate_memory' does this.

     2. If the value changing is a register, all expressions
     containing references to that register, and only those,
     must be removed.

   Because searching the entire hash table for expressions that contain
   a register is very slow, we try to figure out when it isn't necessary.
   Precisely, this is necessary only when expressions have been
   entered in the hash table using this register, and then the value has
   changed, and then another expression wants to be added to refer to
   the register's new value.  This sequence of circumstances is rare
   within any one basic block.

   The vectors `reg_tick' and `reg_in_table' are used to detect this case.
   reg_tick[i] is incremented whenever a value is stored in register i.
   reg_in_table[i] holds -1 if no references to register i have been
   entered in the table; otherwise, it contains the value reg_tick[i] had
   when the references were entered.  If we want to enter a reference
   and reg_in_table[i] != reg_tick[i], we must scan and remove old references.
   Until we want to enter a new entry, the mere fact that the two vectors
   don't match makes the entries be ignored if anyone tries to match them.

   Registers themselves are entered in the hash table as well as in
   the equivalent-register chains.  However, the vectors `reg_tick'
   and `reg_in_table' do not apply to expressions which are simple
   register references.  These expressions are removed from the table
   immediately when they become invalid, and this can be done even if
   we do not immediately search for all the expressions that refer to
   the register.

   A CLOBBER rtx in an instruction invalidates its operand for further
   reuse.  A CLOBBER or SET rtx whose operand is a MEM:BLK
   invalidates everything that resides in memory.

Related expressions:

   Constant expressions that differ only by an additive integer
   are called related.  When a constant expression is put in
   the table, the related expression with no constant term
   is also entered.  These are made to point at each other
   so that it is possible to find out if there exists any
   register equivalent to an expression related to a given expression.  */

/* One plus largest register number used in this function.  */

static int max_reg;

/* One plus largest instruction UID used in this function at time of
   cse_main call.  */

static int max_insn_uid;

/* Length of qty_table vector.  We know in advance we will not need
   a quantity number this big.  */

static int max_qty;

/* Next quantity number to be allocated.
   This is 1 + the largest number needed so far.  */

static int next_qty;

/* Per-qty information tracking.

   `first_reg' and `last_reg' track the head and tail of the
   chain of registers which currently contain this quantity.

   `mode' contains the machine mode of this quantity.

   `const_rtx' holds the rtx of the constant value of this
   quantity, if known.  A summations of the frame/arg pointer
   and a constant can also be entered here.  When this holds
   a known value, `const_insn' is the insn which stored the
   constant value.

   `comparison_{code,const,qty}' are used to track when a
   comparison between a quantity and some constant or register has
   been passed.  In such a case, we know the results of the comparison
   in case we see it again.  These members record a comparison that
   is known to be true.  `comparison_code' holds the rtx code of such
   a comparison, else it is set to UNKNOWN and the other two
   comparison members are undefined.  `comparison_const' holds
   the constant being compared against, or zero if the comparison
   is not against a constant.  `comparison_qty' holds the quantity
   being compared against when the result is known.  If the comparison
   is not with a register, `comparison_qty' is -1.  */

struct qty_table_elem
{
  rtx const_rtx;
  rtx const_insn;
  rtx comparison_const;
  int comparison_qty;
  unsigned int first_reg, last_reg;
  enum machine_mode mode;
  enum rtx_code comparison_code;
};

/* The table of all qtys, indexed by qty number.  */
static struct qty_table_elem *qty_table;

#ifdef HAVE_cc0
/* For machines that have a CC0, we do not record its value in the hash
   table since its use is guaranteed to be the insn immediately following
   its definition and any other insn is presumed to invalidate it.

   Instead, we store below the value last assigned to CC0.  If it should
   happen to be a constant, it is stored in preference to the actual
   assigned value.  In case it is a constant, we store the mode in which
   the constant should be interpreted.  */

static rtx prev_insn_cc0;
static enum machine_mode prev_insn_cc0_mode;
#endif

/* Previous actual insn.  0 if at first insn of basic block.  */

static rtx prev_insn;

/* Insn being scanned.  */

static rtx this_insn;

/* Index by register number, gives the number of the next (or
   previous) register in the chain of registers sharing the same
   value.

   Or -1 if this register is at the end of the chain.

   If reg_qty[N] == N, reg_eqv_table[N].next is undefined.  */

/* Per-register equivalence chain.  */
struct reg_eqv_elem
{
  int next, prev;
};

/* The table of all register equivalence chains.  */
static struct reg_eqv_elem *reg_eqv_table;

struct cse_reg_info
{
  /* Next in hash chain.  */
  struct cse_reg_info *hash_next;

  /* The next cse_reg_info structure in the free or used list.  */
  struct cse_reg_info *next;

  /* Search key */
  unsigned int regno;

  /* The quantity number of the register's current contents.  */
  int reg_qty;

  /* The number of times the register has been altered in the current
     basic block.  */
  int reg_tick;

  /* The REG_TICK value at which rtx's containing this register are
     valid in the hash table.  If this does not equal the current
     reg_tick value, such expressions existing in the hash table are
     invalid.  */
  int reg_in_table;

  /* The SUBREG that was set when REG_TICK was last incremented.  Set
     to -1 if the last store was to the whole register, not a subreg.  */
  unsigned int subreg_ticked;
};

/* A free list of cse_reg_info entries.  */
static struct cse_reg_info *cse_reg_info_free_list;

/* A used list of cse_reg_info entries.  */
static struct cse_reg_info *cse_reg_info_used_list;
static struct cse_reg_info *cse_reg_info_used_list_end;

/* A mapping from registers to cse_reg_info data structures.  */
#define REGHASH_SHIFT	7
#define REGHASH_SIZE	(1 << REGHASH_SHIFT)
#define REGHASH_MASK	(REGHASH_SIZE - 1)
static struct cse_reg_info *reg_hash[REGHASH_SIZE];

#define REGHASH_FN(REGNO)	\
	(((REGNO) ^ ((REGNO) >> REGHASH_SHIFT)) & REGHASH_MASK)

/* The last lookup we did into the cse_reg_info_tree.  This allows us
   to cache repeated lookups.  */
static unsigned int cached_regno;
static struct cse_reg_info *cached_cse_reg_info;

/* A HARD_REG_SET containing all the hard registers for which there is
   currently a REG expression in the hash table.  Note the difference
   from the above variables, which indicate if the REG is mentioned in some
   expression in the table.  */

static HARD_REG_SET hard_regs_in_table;

/* CUID of insn that starts the basic block currently being cse-processed.  */

static int cse_basic_block_start;

/* CUID of insn that ends the basic block currently being cse-processed.  */

static int cse_basic_block_end;

/* Vector mapping INSN_UIDs to cuids.
   The cuids are like uids but increase monotonically always.
   We use them to see whether a reg is used outside a given basic block.  */

static int *uid_cuid;

/* Highest UID in UID_CUID.  */
static int max_uid;

/* Get the cuid of an insn.  */

#define INSN_CUID(INSN) (uid_cuid[INSN_UID (INSN)])

/* Nonzero if this pass has made changes, and therefore it's
   worthwhile to run the garbage collector.  */

static int cse_altered;

/* Nonzero if cse has altered conditional jump insns
   in such a way that jump optimization should be redone.  */

static int cse_jumps_altered;

/* Nonzero if we put a LABEL_REF into the hash table for an INSN without a
   REG_LABEL, we have to rerun jump after CSE to put in the note.  */
static int recorded_label_ref;

/* canon_hash stores 1 in do_not_record
   if it notices a reference to CC0, PC, or some other volatile
   subexpression.  */

static int do_not_record;

#ifdef LOAD_EXTEND_OP

/* Scratch rtl used when looking for load-extended copy of a MEM.  */
static rtx memory_extend_rtx;
#endif

/* canon_hash stores 1 in hash_arg_in_memory
   if it notices a reference to memory within the expression being hashed.  */

static int hash_arg_in_memory;

/* The hash table contains buckets which are chains of `struct table_elt's,
   each recording one expression's information.
   That expression is in the `exp' field.

   The canon_exp field contains a canonical (from the point of view of
   alias analysis) version of the `exp' field.

   Those elements with the same hash code are chained in both directions
   through the `next_same_hash' and `prev_same_hash' fields.

   Each set of expressions with equivalent values
   are on a two-way chain through the `next_same_value'
   and `prev_same_value' fields, and all point with
   the `first_same_value' field at the first element in
   that chain.  The chain is in order of increasing cost.
   Each element's cost value is in its `cost' field.

   The `in_memory' field is nonzero for elements that
   involve any reference to memory.  These elements are removed
   whenever a write is done to an unidentified location in memory.
   To be safe, we assume that a memory address is unidentified unless
   the address is either a symbol constant or a constant plus
   the frame pointer or argument pointer.

   The `related_value' field is used to connect related expressions
   (that differ by adding an integer).
   The related expressions are chained in a circular fashion.
   `related_value' is zero for expressions for which this
   chain is not useful.

   The `cost' field stores the cost of this element's expression.
   The `regcost' field stores the value returned by approx_reg_cost for
   this element's expression.

   The `is_const' flag is set if the element is a constant (including
   a fixed address).

   The `flag' field is used as a temporary during some search routines.

   The `mode' field is usually the same as GET_MODE (`exp'), but
   if `exp' is a CONST_INT and has no machine mode then the `mode'
   field is the mode it was being used as.  Each constant is
   recorded separately for each mode it is used with.  */

struct table_elt
{
  rtx exp;
  rtx canon_exp;
  struct table_elt *next_same_hash;
  struct table_elt *prev_same_hash;
  struct table_elt *next_same_value;
  struct table_elt *prev_same_value;
  struct table_elt *first_same_value;
  struct table_elt *related_value;
  int cost;
  int regcost;
  enum machine_mode mode;
  char in_memory;
  char is_const;
  char flag;
};

/* We don't want a lot of buckets, because we rarely have very many
   things stored in the hash table, and a lot of buckets slows
   down a lot of loops that happen frequently.  */
#define HASH_SHIFT	5
#define HASH_SIZE	(1 << HASH_SHIFT)
#define HASH_MASK	(HASH_SIZE - 1)

/* Compute hash code of X in mode M.  Special-case case where X is a pseudo
   register (hard registers may require `do_not_record' to be set).  */

#define HASH(X, M)	\
 ((GET_CODE (X) == REG && REGNO (X) >= FIRST_PSEUDO_REGISTER	\
  ? (((unsigned) REG << 7) + (unsigned) REG_QTY (REGNO (X)))	\
  : canon_hash (X, M)) & HASH_MASK)

/* Determine whether register number N is considered a fixed register for the
   purpose of approximating register costs.
   It is desirable to replace other regs with fixed regs, to reduce need for
   non-fixed hard regs.
   A reg wins if it is either the frame pointer or designated as fixed.  */
#define FIXED_REGNO_P(N)  \
  ((N) == FRAME_POINTER_REGNUM || (N) == HARD_FRAME_POINTER_REGNUM \
   || fixed_regs[N] || global_regs[N])

/* Compute cost of X, as stored in the `cost' field of a table_elt.  Fixed
   hard registers and pointers into the frame are the cheapest with a cost
   of 0.  Next come pseudos with a cost of one and other hard registers with
   a cost of 2.  Aside from these special cases, call `rtx_cost'.  */

#define CHEAP_REGNO(N) \
  ((N) == FRAME_POINTER_REGNUM || (N) == HARD_FRAME_POINTER_REGNUM 	\
   || (N) == STACK_POINTER_REGNUM || (N) == ARG_POINTER_REGNUM	     	\
   || ((N) >= FIRST_VIRTUAL_REGISTER && (N) <= LAST_VIRTUAL_REGISTER) 	\
   || ((N) < FIRST_PSEUDO_REGISTER					\
       && FIXED_REGNO_P (N) && REGNO_REG_CLASS (N) != NO_REGS))

#define COST(X) (GET_CODE (X) == REG ? 0 : notreg_cost (X, SET))
#define COST_IN(X,OUTER) (GET_CODE (X) == REG ? 0 : notreg_cost (X, OUTER))

/* Get the info associated with register N.  */

#define GET_CSE_REG_INFO(N) 			\
  (((N) == cached_regno && cached_cse_reg_info)	\
   ? cached_cse_reg_info : get_cse_reg_info ((N)))

/* Get the number of times this register has been updated in this
   basic block.  */

#define REG_TICK(N) ((GET_CSE_REG_INFO (N))->reg_tick)

/* Get the point at which REG was recorded in the table.  */

#define REG_IN_TABLE(N) ((GET_CSE_REG_INFO (N))->reg_in_table)

/* Get the SUBREG set at the last increment to REG_TICK (-1 if not a
   SUBREG).  */

#define SUBREG_TICKED(N) ((GET_CSE_REG_INFO (N))->subreg_ticked)

/* Get the quantity number for REG.  */

#define REG_QTY(N) ((GET_CSE_REG_INFO (N))->reg_qty)

/* Determine if the quantity number for register X represents a valid index
   into the qty_table.  */

#define REGNO_QTY_VALID_P(N) (REG_QTY (N) != (int) (N))

static struct table_elt *table[HASH_SIZE];

/* Chain of `struct table_elt's made so far for this function
   but currently removed from the table.  */

static struct table_elt *free_element_chain;

/* Number of `struct table_elt' structures made so far for this function.  */

static int n_elements_made;

/* Maximum value `n_elements_made' has had so far in this compilation
   for functions previously processed.  */

static int max_elements_made;

/* Surviving equivalence class when two equivalence classes are merged
   by recording the effects of a jump in the last insn.  Zero if the
   last insn was not a conditional jump.  */

static struct table_elt *last_jump_equiv_class;

/* Set to the cost of a constant pool reference if one was found for a
   symbolic constant.  If this was found, it means we should try to
   convert constants into constant pool entries if they don't fit in
   the insn.  */

static int constant_pool_entries_cost;

/* Define maximum length of a branch path.  */

#define PATHLENGTH	10

/* This data describes a block that will be processed by cse_basic_block.  */

struct cse_basic_block_data
{
  /* Lowest CUID value of insns in block.  */
  int low_cuid;
  /* Highest CUID value of insns in block.  */
  int high_cuid;
  /* Total number of SETs in block.  */
  int nsets;
  /* Last insn in the block.  */
  rtx last;
  /* Size of current branch path, if any.  */
  int path_size;
  /* Current branch path, indicating which branches will be taken.  */
  struct branch_path
    {
      /* The branch insn.  */
      rtx branch;
      /* Whether it should be taken or not.  AROUND is the same as taken
	 except that it is used when the destination label is not preceded
       by a BARRIER.  */
      enum taken {TAKEN, NOT_TAKEN, AROUND} status;
    } path[PATHLENGTH];
};

/* Nonzero if X has the form (PLUS frame-pointer integer).  We check for
   virtual regs here because the simplify_*_operation routines are called
   by integrate.c, which is called before virtual register instantiation.

   ?!? FIXED_BASE_PLUS_P and NONZERO_BASE_PLUS_P need to move into
   a header file so that their definitions can be shared with the
   simplification routines in simplify-rtx.c.  Until then, do not
   change these macros without also changing the copy in simplify-rtx.c.  */

#define FIXED_BASE_PLUS_P(X)					\
  ((X) == frame_pointer_rtx || (X) == hard_frame_pointer_rtx	\
   || ((X) == arg_pointer_rtx && fixed_regs[ARG_POINTER_REGNUM])\
   || (X) == virtual_stack_vars_rtx				\
   || (X) == virtual_incoming_args_rtx				\
   || (GET_CODE (X) == PLUS && GET_CODE (XEXP (X, 1)) == CONST_INT \
       && (XEXP (X, 0) == frame_pointer_rtx			\
	   || XEXP (X, 0) == hard_frame_pointer_rtx		\
	   || ((X) == arg_pointer_rtx				\
	       && fixed_regs[ARG_POINTER_REGNUM])		\
	   || XEXP (X, 0) == virtual_stack_vars_rtx		\
	   || XEXP (X, 0) == virtual_incoming_args_rtx))	\
   || GET_CODE (X) == ADDRESSOF)

/* Similar, but also allows reference to the stack pointer.

   This used to include FIXED_BASE_PLUS_P, however, we can't assume that
   arg_pointer_rtx by itself is nonzero, because on at least one machine,
   the i960, the arg pointer is zero when it is unused.  */

#define NONZERO_BASE_PLUS_P(X)					\
  ((X) == frame_pointer_rtx || (X) == hard_frame_pointer_rtx	\
   || (X) == virtual_stack_vars_rtx				\
   || (X) == virtual_incoming_args_rtx				\
   || (GET_CODE (X) == PLUS && GET_CODE (XEXP (X, 1)) == CONST_INT \
       && (XEXP (X, 0) == frame_pointer_rtx			\
	   || XEXP (X, 0) == hard_frame_pointer_rtx		\
	   || ((X) == arg_pointer_rtx				\
	       && fixed_regs[ARG_POINTER_REGNUM])		\
	   || XEXP (X, 0) == virtual_stack_vars_rtx		\
	   || XEXP (X, 0) == virtual_incoming_args_rtx))	\
   || (X) == stack_pointer_rtx					\
   || (X) == virtual_stack_dynamic_rtx				\
   || (X) == virtual_outgoing_args_rtx				\
   || (GET_CODE (X) == PLUS && GET_CODE (XEXP (X, 1)) == CONST_INT \
       && (XEXP (X, 0) == stack_pointer_rtx			\
	   || XEXP (X, 0) == virtual_stack_dynamic_rtx		\
	   || XEXP (X, 0) == virtual_outgoing_args_rtx))	\
   || GET_CODE (X) == ADDRESSOF)

static int notreg_cost		PARAMS ((rtx, enum rtx_code));
static int approx_reg_cost_1	PARAMS ((rtx *, void *));
static int approx_reg_cost	PARAMS ((rtx));
static int preferrable		PARAMS ((int, int, int, int));
static void new_basic_block	PARAMS ((void));
static void make_new_qty	PARAMS ((unsigned int, enum machine_mode));
static void make_regs_eqv	PARAMS ((unsigned int, unsigned int));
static void delete_reg_equiv	PARAMS ((unsigned int));
static int mention_regs		PARAMS ((rtx));
static int insert_regs		PARAMS ((rtx, struct table_elt *, int));
static void remove_from_table	PARAMS ((struct table_elt *, unsigned));
static struct table_elt *lookup	PARAMS ((rtx, unsigned, enum machine_mode)),
       *lookup_for_remove PARAMS ((rtx, unsigned, enum machine_mode));
static rtx lookup_as_function	PARAMS ((rtx, enum rtx_code));
static struct table_elt *insert PARAMS ((rtx, struct table_elt *, unsigned,
					 enum machine_mode));
static void merge_equiv_classes PARAMS ((struct table_elt *,
					 struct table_elt *));
static void invalidate		PARAMS ((rtx, enum machine_mode));
static int cse_rtx_varies_p	PARAMS ((rtx, int));
static void remove_invalid_refs	PARAMS ((unsigned int));
static void remove_invalid_subreg_refs	PARAMS ((unsigned int, unsigned int,
						 enum machine_mode));
static void rehash_using_reg	PARAMS ((rtx));
static void invalidate_memory	PARAMS ((void));
static void invalidate_for_call	PARAMS ((void));
static rtx use_related_value	PARAMS ((rtx, struct table_elt *));
static unsigned canon_hash	PARAMS ((rtx, enum machine_mode));
static unsigned canon_hash_string PARAMS ((const char *));
static unsigned safe_hash	PARAMS ((rtx, enum machine_mode));
static int exp_equiv_p		PARAMS ((rtx, rtx, int, int));
static rtx canon_reg		PARAMS ((rtx, rtx));
static void find_best_addr	PARAMS ((rtx, rtx *, enum machine_mode));
static enum rtx_code find_comparison_args PARAMS ((enum rtx_code, rtx *, rtx *,
						   enum machine_mode *,
						   enum machine_mode *));
static rtx fold_rtx		PARAMS ((rtx, rtx));
static rtx equiv_constant	PARAMS ((rtx));
static void record_jump_equiv	PARAMS ((rtx, int));
static void record_jump_cond	PARAMS ((enum rtx_code, enum machine_mode,
					 rtx, rtx, int));
static void cse_insn		PARAMS ((rtx, rtx));
static int addr_affects_sp_p	PARAMS ((rtx));
static void invalidate_from_clobbers PARAMS ((rtx));
static rtx cse_process_notes	PARAMS ((rtx, rtx));
static void cse_around_loop	PARAMS ((rtx));
static void invalidate_skipped_set PARAMS ((rtx, rtx, void *));
static void invalidate_skipped_block PARAMS ((rtx));
static void cse_check_loop_start PARAMS ((rtx, rtx, void *));
static void cse_set_around_loop	PARAMS ((rtx, rtx, rtx));
static rtx cse_basic_block	PARAMS ((rtx, rtx, struct branch_path *, int));
static void count_reg_usage	PARAMS ((rtx, int *, rtx, int));
static int check_for_label_ref	PARAMS ((rtx *, void *));
extern void dump_class          PARAMS ((struct table_elt*));
static struct cse_reg_info * get_cse_reg_info PARAMS ((unsigned int));
static int check_dependence	PARAMS ((rtx *, void *));

static void flush_hash_table	PARAMS ((void));
static bool insn_live_p		PARAMS ((rtx, int *));
static bool set_live_p		PARAMS ((rtx, rtx, int *));
static bool dead_libcall_p	PARAMS ((rtx, int *));
static int cse_change_cc_mode	PARAMS ((rtx *, void *));
static void cse_change_cc_mode_insns PARAMS ((rtx, rtx, rtx));
static enum machine_mode cse_cc_succs PARAMS ((basic_block, rtx, rtx, int));

/* Dump the expressions in the equivalence class indicated by CLASSP.
   This function is used only for debugging.  */
void
dump_class (classp)
     struct table_elt *classp;
{
  struct table_elt *elt;

  fprintf (stderr, "Equivalence chain for ");
  print_rtl (stderr, classp->exp);
  fprintf (stderr, ": \n");

  for (elt = classp->first_same_value; elt; elt = elt->next_same_value)
    {
      print_rtl (stderr, elt->exp);
      fprintf (stderr, "\n");
    }
}

/* Subroutine of approx_reg_cost; called through for_each_rtx.  */

static int
approx_reg_cost_1 (xp, data)
     rtx *xp;
     void *data;
{
  rtx x = *xp;
  int *cost_p = data;

  if (x && GET_CODE (x) == REG)
    {
      unsigned int regno = REGNO (x);

      if (! CHEAP_REGNO (regno))
	{
	  if (regno < FIRST_PSEUDO_REGISTER)
	    {
	      if (SMALL_REGISTER_CLASSES)
		return 1;
	      *cost_p += 2;
	    }
	  else
	    *cost_p += 1;
	}
    }

  return 0;
}

/* Return an estimate of the cost of the registers used in an rtx.
   This is mostly the number of different REG expressions in the rtx;
   however for some exceptions like fixed registers we use a cost of
   0.  If any other hard register reference occurs, return MAX_COST.  */

static int
approx_reg_cost (x)
     rtx x;
{
  int cost = 0;

  if (for_each_rtx (&x, approx_reg_cost_1, (void *) &cost))
    return MAX_COST;

  return cost;
}

/* Return a negative value if an rtx A, whose costs are given by COST_A
   and REGCOST_A, is more desirable than an rtx B.
   Return a positive value if A is less desirable, or 0 if the two are
   equally good.  */
static int
preferrable (cost_a, regcost_a, cost_b, regcost_b)
     int cost_a, regcost_a, cost_b, regcost_b;
{
  /* First, get rid of cases involving expressions that are entirely
     unwanted.  */
  if (cost_a != cost_b)
    {
      if (cost_a == MAX_COST)
	return 1;
      if (cost_b == MAX_COST)
	return -1;
    }

  /* Avoid extending lifetimes of hardregs.  */
  if (regcost_a != regcost_b)
    {
      if (regcost_a == MAX_COST)
	return 1;
      if (regcost_b == MAX_COST)
	return -1;
    }

  /* Normal operation costs take precedence.  */
  if (cost_a != cost_b)
    return cost_a - cost_b;
  /* Only if these are identical consider effects on register pressure.  */
  if (regcost_a != regcost_b)
    return regcost_a - regcost_b;
  return 0;
}

/* Internal function, to compute cost when X is not a register; called
   from COST macro to keep it simple.  */

static int
notreg_cost (x, outer)
     rtx x;
     enum rtx_code outer;
{
  return ((GET_CODE (x) == SUBREG
	   && GET_CODE (SUBREG_REG (x)) == REG
	   && GET_MODE_CLASS (GET_MODE (x)) == MODE_INT
	   && GET_MODE_CLASS (GET_MODE (SUBREG_REG (x))) == MODE_INT
	   && (GET_MODE_SIZE (GET_MODE (x))
	       < GET_MODE_SIZE (GET_MODE (SUBREG_REG (x))))
	   && subreg_lowpart_p (x)
	   && TRULY_NOOP_TRUNCATION (GET_MODE_BITSIZE (GET_MODE (x)),
				     GET_MODE_BITSIZE (GET_MODE (SUBREG_REG (x)))))
	  ? 0
	  : rtx_cost (x, outer) * 2);
}

/* Return an estimate of the cost of computing rtx X.
   One use is in cse, to decide which expression to keep in the hash table.
   Another is in rtl generation, to pick the cheapest way to multiply.
   Other uses like the latter are expected in the future.  */

int
rtx_cost (x, outer_code)
     rtx x;
     enum rtx_code outer_code ATTRIBUTE_UNUSED;
{
  int i, j;
  enum rtx_code code;
  const char *fmt;
  int total;

  if (x == 0)
    return 0;

  /* Compute the default costs of certain things.
     Note that RTX_COSTS can override the defaults.  */

  code = GET_CODE (x);
  switch (code)
    {
    case MULT:
      total = COSTS_N_INSNS (5);
      break;
    case DIV:
    case UDIV:
    case MOD:
    case UMOD:
      total = COSTS_N_INSNS (7);
      break;
    case USE:
      /* Used in loop.c and combine.c as a marker.  */
      total = 0;
      break;
    default:
      total = COSTS_N_INSNS (1);
    }

  switch (code)
    {
    case REG:
      return 0;

    case SUBREG:
      /* If we can't tie these modes, make this expensive.  The larger
	 the mode, the more expensive it is.  */
      if (! MODES_TIEABLE_P (GET_MODE (x), GET_MODE (SUBREG_REG (x))))
	return COSTS_N_INSNS (2
			      + GET_MODE_SIZE (GET_MODE (x)) / UNITS_PER_WORD);
      break;

#ifdef RTX_COSTS
      RTX_COSTS (x, code, outer_code);
#endif
#ifdef CONST_COSTS
      CONST_COSTS (x, code, outer_code);
#endif

    default:
#ifdef DEFAULT_RTX_COSTS
      DEFAULT_RTX_COSTS (x, code, outer_code);
#endif
      break;
    }

  /* Sum the costs of the sub-rtx's, plus cost of this operation,
     which is already in total.  */

  fmt = GET_RTX_FORMAT (code);
  for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
    if (fmt[i] == 'e')
      total += rtx_cost (XEXP (x, i), code);
    else if (fmt[i] == 'E')
      for (j = 0; j < XVECLEN (x, i); j++)
	total += rtx_cost (XVECEXP (x, i, j), code);

  return total;
}

/* Return cost of address expression X.
   Expect that X is properly formed address reference.  */

int
address_cost (x, mode)
     rtx x;
     enum machine_mode mode;
{
  /* The ADDRESS_COST macro does not deal with ADDRESSOF nodes.  But,
     during CSE, such nodes are present.  Using an ADDRESSOF node which
     refers to the address of a REG is a good thing because we can then
     turn (MEM (ADDRESSSOF (REG))) into just plain REG.  */

  if (GET_CODE (x) == ADDRESSOF && REG_P (XEXP ((x), 0)))
    return -1;

  /* We may be asked for cost of various unusual addresses, such as operands
     of push instruction.  It is not worthwhile to complicate writing
     of ADDRESS_COST macro by such cases.  */

  if (!memory_address_p (mode, x))
    return 1000;
#ifdef ADDRESS_COST
  return ADDRESS_COST (x);
#else
  return rtx_cost (x, MEM);
#endif
}


static struct cse_reg_info *
get_cse_reg_info (regno)
     unsigned int regno;
{
  struct cse_reg_info **hash_head = &reg_hash[REGHASH_FN (regno)];
  struct cse_reg_info *p;

  for (p = *hash_head; p != NULL; p = p->hash_next)
    if (p->regno == regno)
      break;

  if (p == NULL)
    {
      /* Get a new cse_reg_info structure.  */
      if (cse_reg_info_free_list)
	{
	  p = cse_reg_info_free_list;
	  cse_reg_info_free_list = p->next;
	}
      else
	p = (struct cse_reg_info *) xmalloc (sizeof (struct cse_reg_info));

      /* Insert into hash table.  */
      p->hash_next = *hash_head;
      *hash_head = p;

      /* Initialize it.  */
      p->reg_tick = 1;
      p->reg_in_table = -1;
      p->subreg_ticked = -1;
      p->reg_qty = regno;
      p->regno = regno;
      p->next = cse_reg_info_used_list;
      cse_reg_info_used_list = p;
      if (!cse_reg_info_used_list_end)
	cse_reg_info_used_list_end = p;
    }

  /* Cache this lookup; we tend to be looking up information about the
     same register several times in a row.  */
  cached_regno = regno;
  cached_cse_reg_info = p;

  return p;
}

/* Clear the hash table and initialize each register with its own quantity,
   for a new basic block.  */

static void
new_basic_block ()
{
  int i;

  next_qty = max_reg;

  /* Clear out hash table state for this pass.  */

  memset ((char *) reg_hash, 0, sizeof reg_hash);

  if (cse_reg_info_used_list)
    {
      cse_reg_info_used_list_end->next = cse_reg_info_free_list;
      cse_reg_info_free_list = cse_reg_info_used_list;
      cse_reg_info_used_list = cse_reg_info_used_list_end = 0;
    }
  cached_cse_reg_info = 0;

  CLEAR_HARD_REG_SET (hard_regs_in_table);

  /* The per-quantity values used to be initialized here, but it is
     much faster to initialize each as it is made in `make_new_qty'.  */

  for (i = 0; i < HASH_SIZE; i++)
    {
      struct table_elt *first;

      first = table[i];
      if (first != NULL)
	{
	  struct table_elt *last = first;

	  table[i] = NULL;

	  while (last->next_same_hash != NULL)
	    last = last->next_same_hash;

	  /* Now relink this hash entire chain into
	     the free element list.  */

	  last->next_same_hash = free_element_chain;
	  free_element_chain = first;
	}
    }

  prev_insn = 0;

#ifdef HAVE_cc0
  prev_insn_cc0 = 0;
#endif
}

/* Say that register REG contains a quantity in mode MODE not in any
   register before and initialize that quantity.  */

static void
make_new_qty (reg, mode)
     unsigned int reg;
     enum machine_mode mode;
{
  int q;
  struct qty_table_elem *ent;
  struct reg_eqv_elem *eqv;

  if (next_qty >= max_qty)
    abort ();

  q = REG_QTY (reg) = next_qty++;
  ent = &qty_table[q];
  ent->first_reg = reg;
  ent->last_reg = reg;
  ent->mode = mode;
  ent->const_rtx = ent->const_insn = NULL_RTX;
  ent->comparison_code = UNKNOWN;

  eqv = &reg_eqv_table[reg];
  eqv->next = eqv->prev = -1;
}

/* Make reg NEW equivalent to reg OLD.
   OLD is not changing; NEW is.  */

static void
make_regs_eqv (new, old)
     unsigned int new, old;
{
  unsigned int lastr, firstr;
  int q = REG_QTY (old);
  struct qty_table_elem *ent;

  ent = &qty_table[q];

  /* Nothing should become eqv until it has a "non-invalid" qty number.  */
  if (! REGNO_QTY_VALID_P (old))
    abort ();

  REG_QTY (new) = q;
  firstr = ent->first_reg;
  lastr = ent->last_reg;

  /* Prefer fixed hard registers to anything.  Prefer pseudo regs to other
     hard regs.  Among pseudos, if NEW will live longer than any other reg
     of the same qty, and that is beyond the current basic block,
     make it the new canonical replacement for this qty.  */
  if (! (firstr < FIRST_PSEUDO_REGISTER && FIXED_REGNO_P (firstr))
      /* Certain fixed registers might be of the class NO_REGS.  This means
	 that not only can they not be allocated by the compiler, but
	 they cannot be used in substitutions or canonicalizations
	 either.  */
      && (new >= FIRST_PSEUDO_REGISTER || REGNO_REG_CLASS (new) != NO_REGS)
      && ((new < FIRST_PSEUDO_REGISTER && FIXED_REGNO_P (new))
	  || (new >= FIRST_PSEUDO_REGISTER
	      && (firstr < FIRST_PSEUDO_REGISTER
		  || ((uid_cuid[REGNO_LAST_UID (new)] > cse_basic_block_end
		       || (uid_cuid[REGNO_FIRST_UID (new)]
			   < cse_basic_block_start))
		      && (uid_cuid[REGNO_LAST_UID (new)]
			  > uid_cuid[REGNO_LAST_UID (firstr)]))))))
    {
      reg_eqv_table[firstr].prev = new;
      reg_eqv_table[new].next = firstr;
      reg_eqv_table[new].prev = -1;
      ent->first_reg = new;
    }
  else
    {
      /* If NEW is a hard reg (known to be non-fixed), insert at end.
	 Otherwise, insert before any non-fixed hard regs that are at the
	 end.  Registers of class NO_REGS cannot be used as an
	 equivalent for anything.  */
      while (lastr < FIRST_PSEUDO_REGISTER && reg_eqv_table[lastr].prev >= 0
	     && (REGNO_REG_CLASS (lastr) == NO_REGS || ! FIXED_REGNO_P (lastr))
	     && new >= FIRST_PSEUDO_REGISTER)
	lastr = reg_eqv_table[lastr].prev;
      reg_eqv_table[new].next = reg_eqv_table[lastr].next;
      if (reg_eqv_table[lastr].next >= 0)
	reg_eqv_table[reg_eqv_table[lastr].next].prev = new;
      else
	qty_table[q].last_reg = new;
      reg_eqv_table[lastr].next = new;
      reg_eqv_table[new].prev = lastr;
    }
}

/* Remove REG from its equivalence class.  */

static void
delete_reg_equiv (reg)
     unsigned int reg;
{
  struct qty_table_elem *ent;
  int q = REG_QTY (reg);
  int p, n;

  /* If invalid, do nothing.  */
  if (q == (int) reg)
    return;

  ent = &qty_table[q];

  p = reg_eqv_table[reg].prev;
  n = reg_eqv_table[reg].next;

  if (n != -1)
    reg_eqv_table[n].prev = p;
  else
    ent->last_reg = p;
  if (p != -1)
    reg_eqv_table[p].next = n;
  else
    ent->first_reg = n;

  REG_QTY (reg) = reg;
}

/* Remove any invalid expressions from the hash table
   that refer to any of the registers contained in expression X.

   Make sure that newly inserted references to those registers
   as subexpressions will be considered valid.

   mention_regs is not called when a register itself
   is being stored in the table.

   Return 1 if we have done something that may have changed the hash code
   of X.  */

static int
mention_regs (x)
     rtx x;
{
  enum rtx_code code;
  int i, j;
  const char *fmt;
  int changed = 0;

  if (x == 0)
    return 0;

  code = GET_CODE (x);
  if (code == REG)
    {
      unsigned int regno = REGNO (x);
      unsigned int endregno
	= regno + (regno >= FIRST_PSEUDO_REGISTER ? 1
		   : HARD_REGNO_NREGS (regno, GET_MODE (x)));
      unsigned int i;

      for (i = regno; i < endregno; i++)
	{
	  if (REG_IN_TABLE (i) >= 0 && REG_IN_TABLE (i) != REG_TICK (i))
	    remove_invalid_refs (i);

	  REG_IN_TABLE (i) = REG_TICK (i);
	  SUBREG_TICKED (i) = -1;
	}

      return 0;
    }

  /* If this is a SUBREG, we don't want to discard other SUBREGs of the same
     pseudo if they don't use overlapping words.  We handle only pseudos
     here for simplicity.  */
  if (code == SUBREG && GET_CODE (SUBREG_REG (x)) == REG
      && REGNO (SUBREG_REG (x)) >= FIRST_PSEUDO_REGISTER)
    {
      unsigned int i = REGNO (SUBREG_REG (x));

      if (REG_IN_TABLE (i) >= 0 && REG_IN_TABLE (i) != REG_TICK (i))
	{
	  /* If REG_IN_TABLE (i) differs from REG_TICK (i) by one, and
	     the last store to this register really stored into this
	     subreg, then remove the memory of this subreg.
	     Otherwise, remove any memory of the entire register and
	     all its subregs from the table.  */
	  if (REG_TICK (i) - REG_IN_TABLE (i) > 1
	      || SUBREG_TICKED (i) != REGNO (SUBREG_REG (x)))
	    remove_invalid_refs (i);
	  else
	    remove_invalid_subreg_refs (i, SUBREG_BYTE (x), GET_MODE (x));
	}

      REG_IN_TABLE (i) = REG_TICK (i);
      SUBREG_TICKED (i) = REGNO (SUBREG_REG (x));
      return 0;
    }

  /* If X is a comparison or a COMPARE and either operand is a register
     that does not have a quantity, give it one.  This is so that a later
     call to record_jump_equiv won't cause X to be assigned a different
     hash code and not found in the table after that call.

     It is not necessary to do this here, since rehash_using_reg can
     fix up the table later, but doing this here eliminates the need to
     call that expensive function in the most common case where the only
     use of the register is in the comparison.  */

  if (code == COMPARE || GET_RTX_CLASS (code) == '<')
    {
      if (GET_CODE (XEXP (x, 0)) == REG
	  && ! REGNO_QTY_VALID_P (REGNO (XEXP (x, 0))))
	if (insert_regs (XEXP (x, 0), NULL, 0))
	  {
	    rehash_using_reg (XEXP (x, 0));
	    changed = 1;
	  }

      if (GET_CODE (XEXP (x, 1)) == REG
	  && ! REGNO_QTY_VALID_P (REGNO (XEXP (x, 1))))
	if (insert_regs (XEXP (x, 1), NULL, 0))
	  {
	    rehash_using_reg (XEXP (x, 1));
	    changed = 1;
	  }
    }

  fmt = GET_RTX_FORMAT (code);
  for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
    if (fmt[i] == 'e')
      changed |= mention_regs (XEXP (x, i));
    else if (fmt[i] == 'E')
      for (j = 0; j < XVECLEN (x, i); j++)
	changed |= mention_regs (XVECEXP (x, i, j));

  return changed;
}

/* Update the register quantities for inserting X into the hash table
   with a value equivalent to CLASSP.
   (If the class does not contain a REG, it is irrelevant.)
   If MODIFIED is nonzero, X is a destination; it is being modified.
   Note that delete_reg_equiv should be called on a register
   before insert_regs is done on that register with MODIFIED != 0.

   Nonzero value means that elements of reg_qty have changed
   so X's hash code may be different.  */

static int
insert_regs (x, classp, modified)
     rtx x;
     struct table_elt *classp;
     int modified;
{
  if (GET_CODE (x) == REG)
    {
      unsigned int regno = REGNO (x);
      int qty_valid;

      /* If REGNO is in the equivalence table already but is of the
	 wrong mode for that equivalence, don't do anything here.  */

      qty_valid = REGNO_QTY_VALID_P (regno);
      if (qty_valid)
	{
	  struct qty_table_elem *ent = &qty_table[REG_QTY (regno)];

	  if (ent->mode != GET_MODE (x))
	    return 0;
	}

      if (modified || ! qty_valid)
	{
	  if (classp)
	    for (classp = classp->first_same_value;
		 classp != 0;
		 classp = classp->next_same_value)
	      if (GET_CODE (classp->exp) == REG
		  && GET_MODE (classp->exp) == GET_MODE (x))
		{
		  make_regs_eqv (regno, REGNO (classp->exp));
		  return 1;
		}

	  /* Mention_regs for a SUBREG checks if REG_TICK is exactly one larger
	     than REG_IN_TABLE to find out if there was only a single preceding
	     invalidation - for the SUBREG - or another one, which would be
	     for the full register.  However, if we find here that REG_TICK
	     indicates that the register is invalid, it means that it has
	     been invalidated in a separate operation.  The SUBREG might be used
	     now (then this is a recursive call), or we might use the full REG
	     now and a SUBREG of it later.  So bump up REG_TICK so that
	     mention_regs will do the right thing.  */
	  if (! modified
	      && REG_IN_TABLE (regno) >= 0
	      && REG_TICK (regno) == REG_IN_TABLE (regno) + 1)
	    REG_TICK (regno)++;
	  make_new_qty (regno, GET_MODE (x));
	  return 1;
	}

      return 0;
    }

  /* If X is a SUBREG, we will likely be inserting the inner register in the
     table.  If that register doesn't have an assigned quantity number at
     this point but does later, the insertion that we will be doing now will
     not be accessible because its hash code will have changed.  So assign
     a quantity number now.  */

  else if (GET_CODE (x) == SUBREG && GET_CODE (SUBREG_REG (x)) == REG
	   && ! REGNO_QTY_VALID_P (REGNO (SUBREG_REG (x))))
    {
      insert_regs (SUBREG_REG (x), NULL, 0);
      mention_regs (x);
      return 1;
    }
  else
    return mention_regs (x);
}

/* Look in or update the hash table.  */

/* Remove table element ELT from use in the table.
   HASH is its hash code, made using the HASH macro.
   It's an argument because often that is known in advance
   and we save much time not recomputing it.  */

static void
remove_from_table (elt, hash)
     struct table_elt *elt;
     unsigned hash;
{
  if (elt == 0)
    return;

  /* Mark this element as removed.  See cse_insn.  */
  elt->first_same_value = 0;

  /* Remove the table element from its equivalence class.  */

  {
    struct table_elt *prev = elt->prev_same_value;
    struct table_elt *next = elt->next_same_value;

    if (next)
      next->prev_same_value = prev;

    if (prev)
      prev->next_same_value = next;
    else
      {
	struct table_elt *newfirst = next;
	while (next)
	  {
	    next->first_same_value = newfirst;
	    next = next->next_same_value;
	  }
      }
  }

  /* Remove the table element from its hash bucket.  */

  {
    struct table_elt *prev = elt->prev_same_hash;
    struct table_elt *next = elt->next_same_hash;

    if (next)
      next->prev_same_hash = prev;

    if (prev)
      prev->next_same_hash = next;
    else if (table[hash] == elt)
      table[hash] = next;
    else
      {
	/* This entry is not in the proper hash bucket.  This can happen
	   when two classes were merged by `merge_equiv_classes'.  Search
	   for the hash bucket that it heads.  This happens only very
	   rarely, so the cost is acceptable.  */
	for (hash = 0; hash < HASH_SIZE; hash++)
	  if (table[hash] == elt)
	    table[hash] = next;
      }
  }

  /* Remove the table element from its related-value circular chain.  */

  if (elt->related_value != 0 && elt->related_value != elt)
    {
      struct table_elt *p = elt->related_value;

      while (p->related_value != elt)
	p = p->related_value;
      p->related_value = elt->related_value;
      if (p->related_value == p)
	p->related_value = 0;
    }

  /* Now add it to the free element chain.  */
  elt->next_same_hash = free_element_chain;
  free_element_chain = elt;
}

/* Look up X in the hash table and return its table element,
   or 0 if X is not in the table.

   MODE is the machine-mode of X, or if X is an integer constant
   with VOIDmode then MODE is the mode with which X will be used.

   Here we are satisfied to find an expression whose tree structure
   looks like X.  */

static struct table_elt *
lookup (x, hash, mode)
     rtx x;
     unsigned hash;
     enum machine_mode mode;
{
  struct table_elt *p;

  for (p = table[hash]; p; p = p->next_same_hash)
    if (mode == p->mode && ((x == p->exp && GET_CODE (x) == REG)
			    || exp_equiv_p (x, p->exp, GET_CODE (x) != REG, 0)))
      return p;

  return 0;
}

/* Like `lookup' but don't care whether the table element uses invalid regs.
   Also ignore discrepancies in the machine mode of a register.  */

static struct table_elt *
lookup_for_remove (x, hash, mode)
     rtx x;
     unsigned hash;
     enum machine_mode mode;
{
  struct table_elt *p;

  if (GET_CODE (x) == REG)
    {
      unsigned int regno = REGNO (x);

      /* Don't check the machine mode when comparing registers;
	 invalidating (REG:SI 0) also invalidates (REG:DF 0).  */
      for (p = table[hash]; p; p = p->next_same_hash)
	if (GET_CODE (p->exp) == REG
	    && REGNO (p->exp) == regno)
	  return p;
    }
  else
    {
      for (p = table[hash]; p; p = p->next_same_hash)
	if (mode == p->mode && (x == p->exp || exp_equiv_p (x, p->exp, 0, 0)))
	  return p;
    }

  return 0;
}

/* Look for an expression equivalent to X and with code CODE.
   If one is found, return that expression.  */

static rtx
lookup_as_function (x, code)
     rtx x;
     enum rtx_code code;
{
  struct table_elt *p
    = lookup (x, safe_hash (x, VOIDmode) & HASH_MASK, GET_MODE (x));

  /* If we are looking for a CONST_INT, the mode doesn't really matter, as
     long as we are narrowing.  So if we looked in vain for a mode narrower
     than word_mode before, look for word_mode now.  */
  if (p == 0 && code == CONST_INT
      && GET_MODE_SIZE (GET_MODE (x)) < GET_MODE_SIZE (word_mode))
    {
      x = copy_rtx (x);
      PUT_MODE (x, word_mode);
      p = lookup (x, safe_hash (x, VOIDmode) & HASH_MASK, word_mode);
    }

  if (p == 0)
    return 0;

  for (p = p->first_same_value; p; p = p->next_same_value)
    if (GET_CODE (p->exp) == code
	/* Make sure this is a valid entry in the table.  */
	&& exp_equiv_p (p->exp, p->exp, 1, 0))
      return p->exp;

  return 0;
}

/* Insert X in the hash table, assuming HASH is its hash code
   and CLASSP is an element of the class it should go in
   (or 0 if a new class should be made).
   It is inserted at the proper position to keep the class in
   the order cheapest first.

   MODE is the machine-mode of X, or if X is an integer constant
   with VOIDmode then MODE is the mode with which X will be used.

   For elements of equal cheapness, the most recent one
   goes in front, except that the first element in the list
   remains first unless a cheaper element is added.  The order of
   pseudo-registers does not matter, as canon_reg will be called to
   find the cheapest when a register is retrieved from the table.

   The in_memory field in the hash table element is set to 0.
   The caller must set it nonzero if appropriate.

   You should call insert_regs (X, CLASSP, MODIFY) before calling here,
   and if insert_regs returns a nonzero value
   you must then recompute its hash code before calling here.

   If necessary, update table showing constant values of quantities.  */

#define CHEAPER(X, Y) \
 (preferrable ((X)->cost, (X)->regcost, (Y)->cost, (Y)->regcost) < 0)

static struct table_elt *
insert (x, classp, hash, mode)
     rtx x;
     struct table_elt *classp;
     unsigned hash;
     enum machine_mode mode;
{
  struct table_elt *elt;

  /* If X is a register and we haven't made a quantity for it,
     something is wrong.  */
  if (GET_CODE (x) == REG && ! REGNO_QTY_VALID_P (REGNO (x)))
    abort ();

  /* If X is a hard register, show it is being put in the table.  */
  if (GET_CODE (x) == REG && REGNO (x) < FIRST_PSEUDO_REGISTER)
    {
      unsigned int regno = REGNO (x);
      unsigned int endregno = regno + HARD_REGNO_NREGS (regno, GET_MODE (x));
      unsigned int i;

      for (i = regno; i < endregno; i++)
	SET_HARD_REG_BIT (hard_regs_in_table, i);
    }

  /* Put an element for X into the right hash bucket.  */

  elt = free_element_chain;
  if (elt)
    free_element_chain = elt->next_same_hash;
  else
    {
      n_elements_made++;
      elt = (struct table_elt *) xmalloc (sizeof (struct table_elt));
    }

  elt->exp = x;
  elt->canon_exp = NULL_RTX;
  elt->cost = COST (x);
  elt->regcost = approx_reg_cost (x);
  elt->next_same_value = 0;
  elt->prev_same_value = 0;
  elt->next_same_hash = table[hash];
  elt->prev_same_hash = 0;
  elt->related_value = 0;
  elt->in_memory = 0;
  elt->mode = mode;
  elt->is_const = (CONSTANT_P (x)
		   /* GNU C++ takes advantage of this for `this'
		      (and other const values).  */
		   || (GET_CODE (x) == REG
		       && RTX_UNCHANGING_P (x)
		       && REGNO (x) >= FIRST_PSEUDO_REGISTER)
		   || FIXED_BASE_PLUS_P (x));

  if (table[hash])
    table[hash]->prev_same_hash = elt;
  table[hash] = elt;

  /* Put it into the proper value-class.  */
  if (classp)
    {
      classp = classp->first_same_value;
      if (CHEAPER (elt, classp))
	/* Insert at the head of the class */
	{
	  struct table_elt *p;
	  elt->next_same_value = classp;
	  classp->prev_same_value = elt;
	  elt->first_same_value = elt;

	  for (p = classp; p; p = p->next_same_value)
	    p->first_same_value = elt;
	}
      else
	{
	  /* Insert not at head of the class.  */
	  /* Put it after the last element cheaper than X.  */
	  struct table_elt *p, *next;

	  for (p = classp; (next = p->next_same_value) && CHEAPER (next, elt);
	       p = next);

	  /* Put it after P and before NEXT.  */
	  elt->next_same_value = next;
	  if (next)
	    next->prev_same_value = elt;

	  elt->prev_same_value = p;
	  p->next_same_value = elt;
	  elt->first_same_value = classp;
	}
    }
  else
    elt->first_same_value = elt;

  /* If this is a constant being set equivalent to a register or a register
     being set equivalent to a constant, note the constant equivalence.

     If this is a constant, it cannot be equivalent to a different constant,
     and a constant is the only thing that can be cheaper than a register.  So
     we know the register is the head of the class (before the constant was
     inserted).

     If this is a register that is not already known equivalent to a
     constant, we must check the entire class.

     If this is a register that is already known equivalent to an insn,
     update the qtys `const_insn' to show that `this_insn' is the latest
     insn making that quantity equivalent to the constant.  */

  if (elt->is_const && classp && GET_CODE (classp->exp) == REG
      && GET_CODE (x) != REG)
    {
      int exp_q = REG_QTY (REGNO (classp->exp));
      struct qty_table_elem *exp_ent = &qty_table[exp_q];

      exp_ent->const_rtx = gen_lowpart_if_possible (exp_ent->mode, x);
      exp_ent->const_insn = this_insn;
    }

  else if (GET_CODE (x) == REG
	   && classp
	   && ! qty_table[REG_QTY (REGNO (x))].const_rtx
	   && ! elt->is_const)
    {
      struct table_elt *p;

      for (p = classp; p != 0; p = p->next_same_value)
	{
	  if (p->is_const && GET_CODE (p->exp) != REG)
	    {
	      int x_q = REG_QTY (REGNO (x));
	      struct qty_table_elem *x_ent = &qty_table[x_q];

	      x_ent->const_rtx
		= gen_lowpart_if_possible (GET_MODE (x), p->exp);
	      x_ent->const_insn = this_insn;
	      break;
	    }
	}
    }

  else if (GET_CODE (x) == REG
	   && qty_table[REG_QTY (REGNO (x))].const_rtx
	   && GET_MODE (x) == qty_table[REG_QTY (REGNO (x))].mode)
    qty_table[REG_QTY (REGNO (x))].const_insn = this_insn;

  /* If this is a constant with symbolic value,
     and it has a term with an explicit integer value,
     link it up with related expressions.  */
  if (GET_CODE (x) == CONST)
    {
      rtx subexp = get_related_value (x);
      unsigned subhash;
      struct table_elt *subelt, *subelt_prev;

      if (subexp != 0)
	{
	  /* Get the integer-free subexpression in the hash table.  */
	  subhash = safe_hash (subexp, mode) & HASH_MASK;
	  subelt = lookup (subexp, subhash, mode);
	  if (subelt == 0)
	    subelt = insert (subexp, NULL, subhash, mode);
	  /* Initialize SUBELT's circular chain if it has none.  */
	  if (subelt->related_value == 0)
	    subelt->related_value = subelt;
	  /* Find the element in the circular chain that precedes SUBELT.  */
	  subelt_prev = subelt;
	  while (subelt_prev->related_value != subelt)
	    subelt_prev = subelt_prev->related_value;
	  /* Put new ELT into SUBELT's circular chain just before SUBELT.
	     This way the element that follows SUBELT is the oldest one.  */
	  elt->related_value = subelt_prev->related_value;
	  subelt_prev->related_value = elt;
	}
    }

  return elt;
}

/* Given two equivalence classes, CLASS1 and CLASS2, put all the entries from
   CLASS2 into CLASS1.  This is done when we have reached an insn which makes
   the two classes equivalent.

   CLASS1 will be the surviving class; CLASS2 should not be used after this
   call.

   Any invalid entries in CLASS2 will not be copied.  */

static void
merge_equiv_classes (class1, class2)
     struct table_elt *class1, *class2;
{
  struct table_elt *elt, *next, *new;

  /* Ensure we start with the head of the classes.  */
  class1 = class1->first_same_value;
  class2 = class2->first_same_value;

  /* If they were already equal, forget it.  */
  if (class1 == class2)
    return;

  for (elt = class2; elt; elt = next)
    {
      unsigned int hash;
      rtx exp = elt->exp;
      enum machine_mode mode = elt->mode;

      next = elt->next_same_value;

      /* Remove old entry, make a new one in CLASS1's class.
	 Don't do this for invalid entries as we cannot find their
	 hash code (it also isn't necessary).  */
      if (GET_CODE (exp) == REG || exp_equiv_p (exp, exp, 1, 0))
	{
	  hash_arg_in_memory = 0;
	  hash = HASH (exp, mode);

	  if (GET_CODE (exp) == REG)
	    delete_reg_equiv (REGNO (exp));

	  remove_from_table (elt, hash);

	  if (insert_regs (exp, class1, 0))
	    {
	      rehash_using_reg (exp);
	      hash = HASH (exp, mode);
	    }
	  new = insert (exp, class1, hash, mode);
	  new->in_memory = hash_arg_in_memory;
	}
    }
}

/* Flush the entire hash table.  */

static void
flush_hash_table ()
{
  int i;
  struct table_elt *p;

  for (i = 0; i < HASH_SIZE; i++)
    for (p = table[i]; p; p = table[i])
      {
	/* Note that invalidate can remove elements
	   after P in the current hash chain.  */
	if (GET_CODE (p->exp) == REG)
	  invalidate (p->exp, p->mode);
	else
	  remove_from_table (p, i);
      }
}

/* Function called for each rtx to check whether true dependence exist.  */
struct check_dependence_data
{
  enum machine_mode mode;
  rtx exp;
};

static int
check_dependence (x, data)
     rtx *x;
     void *data;
{
  struct check_dependence_data *d = (struct check_dependence_data *) data;
  if (*x && GET_CODE (*x) == MEM)
    return true_dependence (d->exp, d->mode, *x, cse_rtx_varies_p);
  else
    return 0;
}

/* Remove from the hash table, or mark as invalid, all expressions whose
   values could be altered by storing in X.  X is a register, a subreg, or
   a memory reference with nonvarying address (because, when a memory
   reference with a varying address is stored in, all memory references are
   removed by invalidate_memory so specific invalidation is superfluous).
   FULL_MODE, if not VOIDmode, indicates that this much should be
   invalidated instead of just the amount indicated by the mode of X.  This
   is only used for bitfield stores into memory.

   A nonvarying address may be just a register or just a symbol reference,
   or it may be either of those plus a numeric offset.  */

static void
invalidate (x, full_mode)
     rtx x;
     enum machine_mode full_mode;
{
  int i;
  struct table_elt *p;

  switch (GET_CODE (x))
    {
    case REG:
      {
	/* If X is a register, dependencies on its contents are recorded
	   through the qty number mechanism.  Just change the qty number of
	   the register, mark it as invalid for expressions that refer to it,
	   and remove it itself.  */
	unsigned int regno = REGNO (x);
	unsigned int hash = HASH (x, GET_MODE (x));

	/* Remove REGNO from any quantity list it might be on and indicate
	   that its value might have changed.  If it is a pseudo, remove its
	   entry from the hash table.

	   For a hard register, we do the first two actions above for any
	   additional hard registers corresponding to X.  Then, if any of these
	   registers are in the table, we must remove any REG entries that
	   overlap these registers.  */

	delete_reg_equiv (regno);
	REG_TICK (regno)++;
	SUBREG_TICKED (regno) = -1;

	if (regno >= FIRST_PSEUDO_REGISTER)
	  {
	    /* Because a register can be referenced in more than one mode,
	       we might have to remove more than one table entry.  */
	    struct table_elt *elt;

	    while ((elt = lookup_for_remove (x, hash, GET_MODE (x))))
	      remove_from_table (elt, hash);
	  }
	else
	  {
	    HOST_WIDE_INT in_table
	      = TEST_HARD_REG_BIT (hard_regs_in_table, regno);
	    unsigned int endregno
	      = regno + HARD_REGNO_NREGS (regno, GET_MODE (x));
	    unsigned int tregno, tendregno, rn;
	    struct table_elt *p, *next;

	    CLEAR_HARD_REG_BIT (hard_regs_in_table, regno);

	    for (rn = regno + 1; rn < endregno; rn++)
	      {
		in_table |= TEST_HARD_REG_BIT (hard_regs_in_table, rn);
		CLEAR_HARD_REG_BIT (hard_regs_in_table, rn);
		delete_reg_equiv (rn);
		REG_TICK (rn)++;
		SUBREG_TICKED (rn) = -1;
	      }

	    if (in_table)
	      for (hash = 0; hash < HASH_SIZE; hash++)
		for (p = table[hash]; p; p = next)
		  {
		    next = p->next_same_hash;

		    if (GET_CODE (p->exp) != REG
			|| REGNO (p->exp) >= FIRST_PSEUDO_REGISTER)
		      continue;

		    tregno = REGNO (p->exp);
		    tendregno
		      = tregno + HARD_REGNO_NREGS (tregno, GET_MODE (p->exp));
		    if (tendregno > regno && tregno < endregno)
		      remove_from_table (p, hash);
		  }
	  }
      }
      return;

    case SUBREG:
      invalidate (SUBREG_REG (x), VOIDmode);
      return;

    case PARALLEL:
      for (i = XVECLEN (x, 0) - 1; i >= 0; --i)
	invalidate (XVECEXP (x, 0, i), VOIDmode);
      return;

    case EXPR_LIST:
      /* This is part of a disjoint return value; extract the location in
	 question ignoring the offset.  */
      invalidate (XEXP (x, 0), VOIDmode);
      return;

    case MEM:
      /* Calculate the canonical version of X here so that
	 true_dependence doesn't generate new RTL for X on each call.  */
      x = canon_rtx (x);

      /* Remove all hash table elements that refer to overlapping pieces of
	 memory.  */
      if (full_mode == VOIDmode)
	full_mode = GET_MODE (x);

      for (i = 0; i < HASH_SIZE; i++)
	{
	  struct table_elt *next;

	  for (p = table[i]; p; p = next)
	    {
	      next = p->next_same_hash;
	      if (p->in_memory)
		{
		  struct check_dependence_data d;

		  /* Just canonicalize the expression once;
		     otherwise each time we call invalidate
		     true_dependence will canonicalize the
		     expression again.  */
		  if (!p->canon_exp)
		    p->canon_exp = canon_rtx (p->exp);
		  d.exp = x;
		  d.mode = full_mode;
		  if (for_each_rtx (&p->canon_exp, check_dependence, &d))
		    remove_from_table (p, i);
		}
	    }
	}
      return;

    default:
      abort ();
    }
}

/* Remove all expressions that refer to register REGNO,
   since they are already invalid, and we are about to
   mark that register valid again and don't want the old
   expressions to reappear as valid.  */

static void
remove_invalid_refs (regno)
     unsigned int regno;
{
  unsigned int i;
  struct table_elt *p, *next;

  for (i = 0; i < HASH_SIZE; i++)
    for (p = table[i]; p; p = next)
      {
	next = p->next_same_hash;
	if (GET_CODE (p->exp) != REG
	    && refers_to_regno_p (regno, regno + 1, p->exp, (rtx *) 0))
	  remove_from_table (p, i);
      }
}

/* Likewise for a subreg with subreg_reg REGNO, subreg_byte OFFSET,
   and mode MODE.  */
static void
remove_invalid_subreg_refs (regno, offset, mode)
     unsigned int regno;
     unsigned int offset;
     enum machine_mode mode;
{
  unsigned int i;
  struct table_elt *p, *next;
  unsigned int end = offset + (GET_MODE_SIZE (mode) - 1);

  for (i = 0; i < HASH_SIZE; i++)
    for (p = table[i]; p; p = next)
      {
	rtx exp = p->exp;
	next = p->next_same_hash;

	if (GET_CODE (exp) != REG
	    && (GET_CODE (exp) != SUBREG
		|| GET_CODE (SUBREG_REG (exp)) != REG
		|| REGNO (SUBREG_REG (exp)) != regno
		|| (((SUBREG_BYTE (exp)
		      + (GET_MODE_SIZE (GET_MODE (exp)) - 1)) >= offset)
		    && SUBREG_BYTE (exp) <= end))
	    && refers_to_regno_p (regno, regno + 1, p->exp, (rtx *) 0))
	  remove_from_table (p, i);
      }
}

/* Recompute the hash codes of any valid entries in the hash table that
   reference X, if X is a register, or SUBREG_REG (X) if X is a SUBREG.

   This is called when we make a jump equivalence.  */

static void
rehash_using_reg (x)
     rtx x;
{
  unsigned int i;
  struct table_elt *p, *next;
  unsigned hash;

  if (GET_CODE (x) == SUBREG)
    x = SUBREG_REG (x);

  /* If X is not a register or if the register is known not to be in any
     valid entries in the table, we have no work to do.  */

  if (GET_CODE (x) != REG
      || REG_IN_TABLE (REGNO (x)) < 0
      || REG_IN_TABLE (REGNO (x)) != REG_TICK (REGNO (x)))
    return;

  /* Scan all hash chains looking for valid entries that mention X.
     If we find one and it is in the wrong hash chain, move it.  We can skip
     objects that are registers, since they are handled specially.  */

  for (i = 0; i < HASH_SIZE; i++)
    for (p = table[i]; p; p = next)
      {
	next = p->next_same_hash;
	if (GET_CODE (p->exp) != REG && reg_mentioned_p (x, p->exp)
	    && exp_equiv_p (p->exp, p->exp, 1, 0)
	    && i != (hash = safe_hash (p->exp, p->mode) & HASH_MASK))
	  {
	    if (p->next_same_hash)
	      p->next_same_hash->prev_same_hash = p->prev_same_hash;

	    if (p->prev_same_hash)
	      p->prev_same_hash->next_same_hash = p->next_same_hash;
	    else
	      table[i] = p->next_same_hash;

	    p->next_same_hash = table[hash];
	    p->prev_same_hash = 0;
	    if (table[hash])
	      table[hash]->prev_same_hash = p;
	    table[hash] = p;
	  }
      }
}

/* Remove from the hash table any expression that is a call-clobbered
   register.  Also update their TICK values.  */

static void
invalidate_for_call ()
{
  unsigned int regno, endregno;
  unsigned int i;
  unsigned hash;
  struct table_elt *p, *next;
  int in_table = 0;

  /* Go through all the hard registers.  For each that is clobbered in
     a CALL_INSN, remove the register from quantity chains and update
     reg_tick if defined.  Also see if any of these registers is currently
     in the table.  */

  for (regno = 0; regno < FIRST_PSEUDO_REGISTER; regno++)
    if (TEST_HARD_REG_BIT (regs_invalidated_by_call, regno))
      {
	delete_reg_equiv (regno);
	if (REG_TICK (regno) >= 0)
	  {
	    REG_TICK (regno)++;
	    SUBREG_TICKED (regno) = -1;
	  }

	in_table |= (TEST_HARD_REG_BIT (hard_regs_in_table, regno) != 0);
      }

  /* In the case where we have no call-clobbered hard registers in the
     table, we are done.  Otherwise, scan the table and remove any
     entry that overlaps a call-clobbered register.  */

  if (in_table)
    for (hash = 0; hash < HASH_SIZE; hash++)
      for (p = table[hash]; p; p = next)
	{
	  next = p->next_same_hash;

	  if (GET_CODE (p->exp) != REG
	      || REGNO (p->exp) >= FIRST_PSEUDO_REGISTER)
	    continue;

	  regno = REGNO (p->exp);
	  endregno = regno + HARD_REGNO_NREGS (regno, GET_MODE (p->exp));

	  for (i = regno; i < endregno; i++)
	    if (TEST_HARD_REG_BIT (regs_invalidated_by_call, i))
	      {
		remove_from_table (p, hash);
		break;
	      }
	}
}

/* Given an expression X of type CONST,
   and ELT which is its table entry (or 0 if it
   is not in the hash table),
   return an alternate expression for X as a register plus integer.
   If none can be found, return 0.  */

static rtx
use_related_value (x, elt)
     rtx x;
     struct table_elt *elt;
{
  struct table_elt *relt = 0;
  struct table_elt *p, *q;
  HOST_WIDE_INT offset;

  /* First, is there anything related known?
     If we have a table element, we can tell from that.
     Otherwise, must look it up.  */

  if (elt != 0 && elt->related_value != 0)
    relt = elt;
  else if (elt == 0 && GET_CODE (x) == CONST)
    {
      rtx subexp = get_related_value (x);
      if (subexp != 0)
	relt = lookup (subexp,
		       safe_hash (subexp, GET_MODE (subexp)) & HASH_MASK,
		       GET_MODE (subexp));
    }

  if (relt == 0)
    return 0;

  /* Search all related table entries for one that has an
     equivalent register.  */

  p = relt;
  while (1)
    {
      /* This loop is strange in that it is executed in two different cases.
	 The first is when X is already in the table.  Then it is searching
	 the RELATED_VALUE list of X's class (RELT).  The second case is when
	 X is not in the table.  Then RELT points to a class for the related
	 value.

	 Ensure that, whatever case we are in, that we ignore classes that have
	 the same value as X.  */

      if (rtx_equal_p (x, p->exp))
	q = 0;
      else
	for (q = p->first_same_value; q; q = q->next_same_value)
	  if (GET_CODE (q->exp) == REG)
	    break;

      if (q)
	break;

      p = p->related_value;

      /* We went all the way around, so there is nothing to be found.
	 Alternatively, perhaps RELT was in the table for some other reason
	 and it has no related values recorded.  */
      if (p == relt || p == 0)
	break;
    }

  if (q == 0)
    return 0;

  offset = (get_integer_term (x) - get_integer_term (p->exp));
  /* Note: OFFSET may be 0 if P->xexp and X are related by commutativity.  */
  return plus_constant (q->exp, offset);
}

/* Hash a string.  Just add its bytes up.  */
static inline unsigned
canon_hash_string (ps)
     const char *ps;
{
  unsigned hash = 0;
  const unsigned char *p = (const unsigned char *) ps;

  if (p)
    while (*p)
      hash += *p++;

  return hash;
}

/* Hash an rtx.  We are careful to make sure the value is never negative.
   Equivalent registers hash identically.
   MODE is used in hashing for CONST_INTs only;
   otherwise the mode of X is used.

   Store 1 in do_not_record if any subexpression is volatile.

   Store 1 in hash_arg_in_memory if X contains a MEM rtx
   which does not have the RTX_UNCHANGING_P bit set.

   Note that cse_insn knows that the hash code of a MEM expression
   is just (int) MEM plus the hash code of the address.  */

static unsigned
canon_hash (x, mode)
     rtx x;
     enum machine_mode mode;
{
  int i, j;
  unsigned hash = 0;
  enum rtx_code code;
  const char *fmt;

  /* repeat is used to turn tail-recursion into iteration.  */
 repeat:
  if (x == 0)
    return hash;

  code = GET_CODE (x);
  switch (code)
    {
    case REG:
      {
	unsigned int regno = REGNO (x);
	bool record;

	/* On some machines, we can't record any non-fixed hard register,
	   because extending its life will cause reload problems.  We
	   consider ap, fp, sp, gp to be fixed for this purpose.

	   We also consider CCmode registers to be fixed for this purpose;
	   failure to do so leads to failure to simplify 0<100 type of
	   conditionals.

	   On all machines, we can't record any global registers.
	   Nor should we record any register that is in a small
	   class, as defined by CLASS_LIKELY_SPILLED_P.  */

	if (regno >= FIRST_PSEUDO_REGISTER)
	  record = true;
	else if (x == frame_pointer_rtx
		 || x == hard_frame_pointer_rtx
		 || x == arg_pointer_rtx
		 || x == stack_pointer_rtx
		 || x == pic_offset_table_rtx)
	  record = true;
	else if (global_regs[regno])
	  record = false;
	else if (fixed_regs[regno])
	  record = true;
	else if (GET_MODE_CLASS (GET_MODE (x)) == MODE_CC)
	  record = true;
	else if (SMALL_REGISTER_CLASSES)
	  record = false;
	else if (CLASS_LIKELY_SPILLED_P (REGNO_REG_CLASS (regno)))
	  record = false;
	else
	  record = true;
	    
	if (!record)
	  {
	    do_not_record = 1;
	    return 0;
	  }

	hash += ((unsigned) REG << 7) + (unsigned) REG_QTY (regno);
	return hash;
      }

    /* We handle SUBREG of a REG specially because the underlying
       reg changes its hash value with every value change; we don't
       want to have to forget unrelated subregs when one subreg changes.  */
    case SUBREG:
      {
	if (GET_CODE (SUBREG_REG (x)) == REG)
	  {
	    hash += (((unsigned) SUBREG << 7)
		     + REGNO (SUBREG_REG (x))
		     + (SUBREG_BYTE (x) / UNITS_PER_WORD));
	    return hash;
	  }
	break;
      }

    case CONST_INT:
      {
	unsigned HOST_WIDE_INT tem = INTVAL (x);
	hash += ((unsigned) CONST_INT << 7) + (unsigned) mode + tem;
	return hash;
      }

    case CONST_DOUBLE:
      /* This is like the general case, except that it only counts
	 the integers representing the constant.  */
      hash += (unsigned) code + (unsigned) GET_MODE (x);
      if (GET_MODE (x) != VOIDmode)
	hash += real_hash (CONST_DOUBLE_REAL_VALUE (x));
      else
	hash += ((unsigned) CONST_DOUBLE_LOW (x)
		 + (unsigned) CONST_DOUBLE_HIGH (x));
      return hash;

    case CONST_VECTOR:
      {
	int units;
	rtx elt;

	units = CONST_VECTOR_NUNITS (x);

	for (i = 0; i < units; ++i)
	  {
	    elt = CONST_VECTOR_ELT (x, i);
	    hash += canon_hash (elt, GET_MODE (elt));
	  }

	return hash;
      }

      /* Assume there is only one rtx object for any given label.  */
    case LABEL_REF:
      hash += ((unsigned) LABEL_REF << 7) + (unsigned long) XEXP (x, 0);
      return hash;

    case SYMBOL_REF:
      hash += ((unsigned) SYMBOL_REF << 7) + (unsigned long) XSTR (x, 0);
      return hash;

    case MEM:
      /* We don't record if marked volatile or if BLKmode since we don't
	 know the size of the move.  */
      if (MEM_VOLATILE_P (x) || GET_MODE (x) == BLKmode)
	{
	  do_not_record = 1;
	  return 0;
	}
      if (! RTX_UNCHANGING_P (x) || FIXED_BASE_PLUS_P (XEXP (x, 0)))
	{
	  hash_arg_in_memory = 1;
	}
      /* Now that we have already found this special case,
	 might as well speed it up as much as possible.  */
      hash += (unsigned) MEM;
      x = XEXP (x, 0);
      goto repeat;

    case USE:
      /* A USE that mentions non-volatile memory needs special
	 handling since the MEM may be BLKmode which normally
	 prevents an entry from being made.  Pure calls are
	 marked by a USE which mentions BLKmode memory.  */
      if (GET_CODE (XEXP (x, 0)) == MEM
	  && ! MEM_VOLATILE_P (XEXP (x, 0)))
	{
	  hash += (unsigned) USE;
	  x = XEXP (x, 0);

	  if (! RTX_UNCHANGING_P (x) || FIXED_BASE_PLUS_P (XEXP (x, 0)))
	    hash_arg_in_memory = 1;

	  /* Now that we have already found this special case,
	     might as well speed it up as much as possible.  */
	  hash += (unsigned) MEM;
	  x = XEXP (x, 0);
	  goto repeat;
	}
      break;

    case PRE_DEC:
    case PRE_INC:
    case POST_DEC:
    case POST_INC:
    case PRE_MODIFY:
    case POST_MODIFY:
    case PC:
    case CC0:
    case CALL:
    case UNSPEC_VOLATILE:
      do_not_record = 1;
      return 0;

    case ASM_OPERANDS:
      if (MEM_VOLATILE_P (x))
	{
	  do_not_record = 1;
	  return 0;
	}
      else
	{
	  /* We don't want to take the filename and line into account.  */
	  hash += (unsigned) code + (unsigned) GET_MODE (x)
	    + canon_hash_string (ASM_OPERANDS_TEMPLATE (x))
	    + canon_hash_string (ASM_OPERANDS_OUTPUT_CONSTRAINT (x))
	    + (unsigned) ASM_OPERANDS_OUTPUT_IDX (x);

	  if (ASM_OPERANDS_INPUT_LENGTH (x))
	    {
	      for (i = 1; i < ASM_OPERANDS_INPUT_LENGTH (x); i++)
		{
		  hash += (canon_hash (ASM_OPERANDS_INPUT (x, i),
				       GET_MODE (ASM_OPERANDS_INPUT (x, i)))
			   + canon_hash_string (ASM_OPERANDS_INPUT_CONSTRAINT
						(x, i)));
		}

	      hash += canon_hash_string (ASM_OPERANDS_INPUT_CONSTRAINT (x, 0));
	      x = ASM_OPERANDS_INPUT (x, 0);
	      mode = GET_MODE (x);
	      goto repeat;
	    }

	  return hash;
	}
      break;

    default:
      break;
    }

  i = GET_RTX_LENGTH (code) - 1;
  hash += (unsigned) code + (unsigned) GET_MODE (x);
  fmt = GET_RTX_FORMAT (code);
  for (; i >= 0; i--)
    {
      if (fmt[i] == 'e')
	{
	  rtx tem = XEXP (x, i);

	  /* If we are about to do the last recursive call
	     needed at this level, change it into iteration.
	     This function  is called enough to be worth it.  */
	  if (i == 0)
	    {
	      x = tem;
	      goto repeat;
	    }
	  hash += canon_hash (tem, 0);
	}
      else if (fmt[i] == 'E')
	for (j = 0; j < XVECLEN (x, i); j++)
	  hash += canon_hash (XVECEXP (x, i, j), 0);
      else if (fmt[i] == 's')
	hash += canon_hash_string (XSTR (x, i));
      else if (fmt[i] == 'i')
	{
	  unsigned tem = XINT (x, i);
	  hash += tem;
	}
      else if (fmt[i] == '0' || fmt[i] == 't')
	/* Unused.  */
	;
      else
	abort ();
    }
  return hash;
}

/* Like canon_hash but with no side effects.  */

static unsigned
safe_hash (x, mode)
     rtx x;
     enum machine_mode mode;
{
  int save_do_not_record = do_not_record;
  int save_hash_arg_in_memory = hash_arg_in_memory;
  unsigned hash = canon_hash (x, mode);
  hash_arg_in_memory = save_hash_arg_in_memory;
  do_not_record = save_do_not_record;
  return hash;
}

/* Return 1 iff X and Y would canonicalize into the same thing,
   without actually constructing the canonicalization of either one.
   If VALIDATE is nonzero,
   we assume X is an expression being processed from the rtl
   and Y was found in the hash table.  We check register refs
   in Y for being marked as valid.

   If EQUAL_VALUES is nonzero, we allow a register to match a constant value
   that is known to be in the register.  Ordinarily, we don't allow them
   to match, because letting them match would cause unpredictable results
   in all the places that search a hash table chain for an equivalent
   for a given value.  A possible equivalent that has different structure
   has its hash code computed from different data.  Whether the hash code
   is the same as that of the given value is pure luck.  */

static int
exp_equiv_p (x, y, validate, equal_values)
     rtx x, y;
     int validate;
     int equal_values;
{
  int i, j;
  enum rtx_code code;
  const char *fmt;

  /* Note: it is incorrect to assume an expression is equivalent to itself
     if VALIDATE is nonzero.  */
  if (x == y && !validate)
    return 1;
  if (x == 0 || y == 0)
    return x == y;

  code = GET_CODE (x);
  if (code != GET_CODE (y))
    {
      if (!equal_values)
	return 0;

      /* If X is a constant and Y is a register or vice versa, they may be
	 equivalent.  We only have to validate if Y is a register.  */
      if (CONSTANT_P (x) && GET_CODE (y) == REG
	  && REGNO_QTY_VALID_P (REGNO (y)))
	{
	  int y_q = REG_QTY (REGNO (y));
	  struct qty_table_elem *y_ent = &qty_table[y_q];

	  if (GET_MODE (y) == y_ent->mode
	      && rtx_equal_p (x, y_ent->const_rtx)
	      && (! validate || REG_IN_TABLE (REGNO (y)) == REG_TICK (REGNO (y))))
	    return 1;
	}

      if (CONSTANT_P (y) && code == REG
	  && REGNO_QTY_VALID_P (REGNO (x)))
	{
	  int x_q = REG_QTY (REGNO (x));
	  struct qty_table_elem *x_ent = &qty_table[x_q];

	  if (GET_MODE (x) == x_ent->mode
	      && rtx_equal_p (y, x_ent->const_rtx))
	    return 1;
	}

      return 0;
    }

  /* (MULT:SI x y) and (MULT:HI x y) are NOT equivalent.  */
  if (GET_MODE (x) != GET_MODE (y))
    return 0;

  switch (code)
    {
    case PC:
    case CC0:
    case CONST_INT:
      return x == y;

    case LABEL_REF:
      return XEXP (x, 0) == XEXP (y, 0);

    case SYMBOL_REF:
      return XSTR (x, 0) == XSTR (y, 0);

    case REG:
      {
	unsigned int regno = REGNO (y);
	unsigned int endregno
	  = regno + (regno >= FIRST_PSEUDO_REGISTER ? 1
		     : HARD_REGNO_NREGS (regno, GET_MODE (y)));
	unsigned int i;

	/* If the quantities are not the same, the expressions are not
	   equivalent.  If there are and we are not to validate, they
	   are equivalent.  Otherwise, ensure all regs are up-to-date.  */

	if (REG_QTY (REGNO (x)) != REG_QTY (regno))
	  return 0;

	if (! validate)
	  return 1;

	for (i = regno; i < endregno; i++)
	  if (REG_IN_TABLE (i) != REG_TICK (i))
	    return 0;

	return 1;
      }

    /*  For commutative operations, check both orders.  */
    case PLUS:
    case MULT:
    case AND:
    case IOR:
    case XOR:
    case NE:
    case EQ:
      return ((exp_equiv_p (XEXP (x, 0), XEXP (y, 0), validate, equal_values)
	       && exp_equiv_p (XEXP (x, 1), XEXP (y, 1),
			       validate, equal_values))
	      || (exp_equiv_p (XEXP (x, 0), XEXP (y, 1),
			       validate, equal_values)
		  && exp_equiv_p (XEXP (x, 1), XEXP (y, 0),
				  validate, equal_values)));

    case ASM_OPERANDS:
      /* We don't use the generic code below because we want to
	 disregard filename and line numbers.  */

      /* A volatile asm isn't equivalent to any other.  */
      if (MEM_VOLATILE_P (x) || MEM_VOLATILE_P (y))
	return 0;

      if (GET_MODE (x) != GET_MODE (y)
	  || strcmp (ASM_OPERANDS_TEMPLATE (x), ASM_OPERANDS_TEMPLATE (y))
	  || strcmp (ASM_OPERANDS_OUTPUT_CONSTRAINT (x),
		     ASM_OPERANDS_OUTPUT_CONSTRAINT (y))
	  || ASM_OPERANDS_OUTPUT_IDX (x) != ASM_OPERANDS_OUTPUT_IDX (y)
	  || ASM_OPERANDS_INPUT_LENGTH (x) != ASM_OPERANDS_INPUT_LENGTH (y))
	return 0;

      if (ASM_OPERANDS_INPUT_LENGTH (x))
	{
	  for (i = ASM_OPERANDS_INPUT_LENGTH (x) - 1; i >= 0; i--)
	    if (! exp_equiv_p (ASM_OPERANDS_INPUT (x, i),
			       ASM_OPERANDS_INPUT (y, i),
			       validate, equal_values)
		|| strcmp (ASM_OPERANDS_INPUT_CONSTRAINT (x, i),
			   ASM_OPERANDS_INPUT_CONSTRAINT (y, i)))
	      return 0;
	}

      return 1;

    default:
      break;
    }

  /* Compare the elements.  If any pair of corresponding elements
     fail to match, return 0 for the whole things.  */

  fmt = GET_RTX_FORMAT (code);
  for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
    {
      switch (fmt[i])
	{
	case 'e':
	  if (! exp_equiv_p (XEXP (x, i), XEXP (y, i), validate, equal_values))
	    return 0;
	  break;

	case 'E':
	  if (XVECLEN (x, i) != XVECLEN (y, i))
	    return 0;
	  for (j = 0; j < XVECLEN (x, i); j++)
	    if (! exp_equiv_p (XVECEXP (x, i, j), XVECEXP (y, i, j),
			       validate, equal_values))
	      return 0;
	  break;

	case 's':
	  if (strcmp (XSTR (x, i), XSTR (y, i)))
	    return 0;
	  break;

	case 'i':
	  if (XINT (x, i) != XINT (y, i))
	    return 0;
	  break;

	case 'w':
	  if (XWINT (x, i) != XWINT (y, i))
	    return 0;
	  break;

	case '0':
	case 't':
	  break;

	default:
	  abort ();
	}
    }

  return 1;
}

/* Return 1 if X has a value that can vary even between two
   executions of the program.  0 means X can be compared reliably
   against certain constants or near-constants.  */

static int
cse_rtx_varies_p (x, from_alias)
     rtx x;
     int from_alias;
{
  /* We need not check for X and the equivalence class being of the same
     mode because if X is equivalent to a constant in some mode, it
     doesn't vary in any mode.  */

  if (GET_CODE (x) == REG
      && REGNO_QTY_VALID_P (REGNO (x)))
    {
      int x_q = REG_QTY (REGNO (x));
      struct qty_table_elem *x_ent = &qty_table[x_q];

      if (GET_MODE (x) == x_ent->mode
	  && x_ent->const_rtx != NULL_RTX)
	return 0;
    }

  if (GET_CODE (x) == PLUS
      && GET_CODE (XEXP (x, 1)) == CONST_INT
      && GET_CODE (XEXP (x, 0)) == REG
      && REGNO_QTY_VALID_P (REGNO (XEXP (x, 0))))
    {
      int x0_q = REG_QTY (REGNO (XEXP (x, 0)));
      struct qty_table_elem *x0_ent = &qty_table[x0_q];

      if ((GET_MODE (XEXP (x, 0)) == x0_ent->mode)
	  && x0_ent->const_rtx != NULL_RTX)
	return 0;
    }

  /* This can happen as the result of virtual register instantiation, if
     the initial constant is too large to be a valid address.  This gives
     us a three instruction sequence, load large offset into a register,
     load fp minus a constant into a register, then a MEM which is the
     sum of the two `constant' registers.  */
  if (GET_CODE (x) == PLUS
      && GET_CODE (XEXP (x, 0)) == REG
      && GET_CODE (XEXP (x, 1)) == REG
      && REGNO_QTY_VALID_P (REGNO (XEXP (x, 0)))
      && REGNO_QTY_VALID_P (REGNO (XEXP (x, 1))))
    {
      int x0_q = REG_QTY (REGNO (XEXP (x, 0)));
      int x1_q = REG_QTY (REGNO (XEXP (x, 1)));
      struct qty_table_elem *x0_ent = &qty_table[x0_q];
      struct qty_table_elem *x1_ent = &qty_table[x1_q];

      if ((GET_MODE (XEXP (x, 0)) == x0_ent->mode)
	  && x0_ent->const_rtx != NULL_RTX
	  && (GET_MODE (XEXP (x, 1)) == x1_ent->mode)
	  && x1_ent->const_rtx != NULL_RTX)
	return 0;
    }

  return rtx_varies_p (x, from_alias);
}

/* Canonicalize an expression:
   replace each register reference inside it
   with the "oldest" equivalent register.

   If INSN is nonzero and we are replacing a pseudo with a hard register
   or vice versa, validate_change is used to ensure that INSN remains valid
   after we make our substitution.  The calls are made with IN_GROUP nonzero
   so apply_change_group must be called upon the outermost return from this
   function (unless INSN is zero).  The result of apply_change_group can
   generally be discarded since the changes we are making are optional.  */

static rtx
canon_reg (x, insn)
     rtx x;
     rtx insn;
{
  int i;
  enum rtx_code code;
  const char *fmt;

  if (x == 0)
    return x;

  code = GET_CODE (x);
  switch (code)
    {
    case PC:
    case CC0:
    case CONST:
    case CONST_INT:
    case CONST_DOUBLE:
    case CONST_VECTOR:
    case SYMBOL_REF:
    case LABEL_REF:
    case ADDR_VEC:
    case ADDR_DIFF_VEC:
      return x;

    case REG:
      {
	int first;
	int q;
	struct qty_table_elem *ent;

	/* Never replace a hard reg, because hard regs can appear
	   in more than one machine mode, and we must preserve the mode
	   of each occurrence.  Also, some hard regs appear in
	   MEMs that are shared and mustn't be altered.  Don't try to
	   replace any reg that maps to a reg of class NO_REGS.  */
	if (REGNO (x) < FIRST_PSEUDO_REGISTER
	    || ! REGNO_QTY_VALID_P (REGNO (x)))
	  return x;

	q = REG_QTY (REGNO (x));
	ent = &qty_table[q];
	first = ent->first_reg;
	return (first >= FIRST_PSEUDO_REGISTER ? regno_reg_rtx[first]
		: REGNO_REG_CLASS (first) == NO_REGS ? x
		: gen_rtx_REG (ent->mode, first));
      }

    default:
      break;
    }

  fmt = GET_RTX_FORMAT (code);
  for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
    {
      int j;

      if (fmt[i] == 'e')
	{
	  rtx new = canon_reg (XEXP (x, i), insn);
	  int insn_code;

	  /* If replacing pseudo with hard reg or vice versa, ensure the
	     insn remains valid.  Likewise if the insn has MATCH_DUPs.  */
	  if (insn != 0 && new != 0
	      && GET_CODE (new) == REG && GET_CODE (XEXP (x, i)) == REG
	      && (((REGNO (new) < FIRST_PSEUDO_REGISTER)
		   != (REGNO (XEXP (x, i)) < FIRST_PSEUDO_REGISTER))
		  || (insn_code = recog_memoized (insn)) < 0
		  || insn_data[insn_code].n_dups > 0))
	    validate_change (insn, &XEXP (x, i), new, 1);
	  else
	    XEXP (x, i) = new;
	}
      else if (fmt[i] == 'E')
	for (j = 0; j < XVECLEN (x, i); j++)
	  XVECEXP (x, i, j) = canon_reg (XVECEXP (x, i, j), insn);
    }

  return x;
}

/* LOC is a location within INSN that is an operand address (the contents of
   a MEM).  Find the best equivalent address to use that is valid for this
   insn.

   On most CISC machines, complicated address modes are costly, and rtx_cost
   is a good approximation for that cost.  However, most RISC machines have
   only a few (usually only one) memory reference formats.  If an address is
   valid at all, it is often just as cheap as any other address.  Hence, for
   RISC machines, we use the configuration macro `ADDRESS_COST' to compare the
   costs of various addresses.  For two addresses of equal cost, choose the one
   with the highest `rtx_cost' value as that has the potential of eliminating
   the most insns.  For equal costs, we choose the first in the equivalence
   class.  Note that we ignore the fact that pseudo registers are cheaper
   than hard registers here because we would also prefer the pseudo registers.
  */

static void
find_best_addr (insn, loc, mode)
     rtx insn;
     rtx *loc;
     enum machine_mode mode;
{
  struct table_elt *elt;
  rtx addr = *loc;
#ifdef ADDRESS_COST
  struct table_elt *p;
  int found_better = 1;
#endif
  int save_do_not_record = do_not_record;
  int save_hash_arg_in_memory = hash_arg_in_memory;
  int addr_volatile;
  int regno;
  unsigned hash;

  /* Do not try to replace constant addresses or addresses of local and
     argument slots.  These MEM expressions are made only once and inserted
     in many instructions, as well as being used to control symbol table
     output.  It is not safe to clobber them.

     There are some uncommon cases where the address is already in a register
     for some reason, but we cannot take advantage of that because we have
     no easy way to unshare the MEM.  In addition, looking up all stack
     addresses is costly.  */
  if ((GET_CODE (addr) == PLUS
       && GET_CODE (XEXP (addr, 0)) == REG
       && GET_CODE (XEXP (addr, 1)) == CONST_INT
       && (regno = REGNO (XEXP (addr, 0)),
	   regno == FRAME_POINTER_REGNUM || regno == HARD_FRAME_POINTER_REGNUM
	   || regno == ARG_POINTER_REGNUM))
      || (GET_CODE (addr) == REG
	  && (regno = REGNO (addr), regno == FRAME_POINTER_REGNUM
	      || regno == HARD_FRAME_POINTER_REGNUM
	      || regno == ARG_POINTER_REGNUM))
      || GET_CODE (addr) == ADDRESSOF
      || CONSTANT_ADDRESS_P (addr))
    return;

  /* If this address is not simply a register, try to fold it.  This will
     sometimes simplify the expression.  Many simplifications
     will not be valid, but some, usually applying the associative rule, will
     be valid and produce better code.  */
  if (GET_CODE (addr) != REG)
    {
      rtx folded = fold_rtx (copy_rtx (addr), NULL_RTX);
      int addr_folded_cost = address_cost (folded, mode);
      int addr_cost = address_cost (addr, mode);

      if ((addr_folded_cost < addr_cost
	   || (addr_folded_cost == addr_cost
	       /* ??? The rtx_cost comparison is left over from an older
		  version of this code.  It is probably no longer helpful.  */
	       && (rtx_cost (folded, MEM) > rtx_cost (addr, MEM)
		   || approx_reg_cost (folded) < approx_reg_cost (addr))))
	  && validate_change (insn, loc, folded, 0))
	addr = folded;
    }

  /* If this address is not in the hash table, we can't look for equivalences
     of the whole address.  Also, ignore if volatile.  */

  do_not_record = 0;
  hash = HASH (addr, Pmode);
  addr_volatile = do_not_record;
  do_not_record = save_do_not_record;
  hash_arg_in_memory = save_hash_arg_in_memory;

  if (addr_volatile)
    return;

  elt = lookup (addr, hash, Pmode);

#ifndef ADDRESS_COST
  if (elt)
    {
      int our_cost = elt->cost;

      /* Find the lowest cost below ours that works.  */
      for (elt = elt->first_same_value; elt; elt = elt->next_same_value)
	if (elt->cost < our_cost
	    && (GET_CODE (elt->exp) == REG
		|| exp_equiv_p (elt->exp, elt->exp, 1, 0))
	    && validate_change (insn, loc,
				canon_reg (copy_rtx (elt->exp), NULL_RTX), 0))
	  return;
    }
#else

  if (elt)
    {
      /* We need to find the best (under the criteria documented above) entry
	 in the class that is valid.  We use the `flag' field to indicate
	 choices that were invalid and iterate until we can't find a better
	 one that hasn't already been tried.  */

      for (p = elt->first_same_value; p; p = p->next_same_value)
	p->flag = 0;

      while (found_better)
	{
	  int best_addr_cost = address_cost (*loc, mode);
	  int best_rtx_cost = (elt->cost + 1) >> 1;
	  int exp_cost;
	  struct table_elt *best_elt = elt;

	  found_better = 0;
	  for (p = elt->first_same_value; p; p = p->next_same_value)
	    if (! p->flag)
	      {
		if ((GET_CODE (p->exp) == REG
		     || exp_equiv_p (p->exp, p->exp, 1, 0))
		    && ((exp_cost = address_cost (p->exp, mode)) < best_addr_cost
			|| (exp_cost == best_addr_cost
			    && ((p->cost + 1) >> 1) > best_rtx_cost)))
		  {
		    found_better = 1;
		    best_addr_cost = exp_cost;
		    best_rtx_cost = (p->cost + 1) >> 1;
		    best_elt = p;
		  }
	      }

	  if (found_better)
	    {
	      if (validate_change (insn, loc,
				   canon_reg (copy_rtx (best_elt->exp),
					      NULL_RTX), 0))
		return;
	      else
		best_elt->flag = 1;
	    }
	}
    }

  /* If the address is a binary operation with the first operand a register
     and the second a constant, do the same as above, but looking for
     equivalences of the register.  Then try to simplify before checking for
     the best address to use.  This catches a few cases:  First is when we
     have REG+const and the register is another REG+const.  We can often merge
     the constants and eliminate one insn and one register.  It may also be
     that a machine has a cheap REG+REG+const.  Finally, this improves the
     code on the Alpha for unaligned byte stores.  */

  if (flag_expensive_optimizations
      && (GET_RTX_CLASS (GET_CODE (*loc)) == '2'
	  || GET_RTX_CLASS (GET_CODE (*loc)) == 'c')
      && GET_CODE (XEXP (*loc, 0)) == REG
      && GET_CODE (XEXP (*loc, 1)) == CONST_INT)
    {
      rtx c = XEXP (*loc, 1);

      do_not_record = 0;
      hash = HASH (XEXP (*loc, 0), Pmode);
      do_not_record = save_do_not_record;
      hash_arg_in_memory = save_hash_arg_in_memory;

      elt = lookup (XEXP (*loc, 0), hash, Pmode);
      if (elt == 0)
	return;

      /* We need to find the best (under the criteria documented above) entry
	 in the class that is valid.  We use the `flag' field to indicate
	 choices that were invalid and iterate until we can't find a better
	 one that hasn't already been tried.  */

      for (p = elt->first_same_value; p; p = p->next_same_value)
	p->flag = 0;

      while (found_better)
	{
	  int best_addr_cost = address_cost (*loc, mode);
	  int best_rtx_cost = (COST (*loc) + 1) >> 1;
	  struct table_elt *best_elt = elt;
	  rtx best_rtx = *loc;
	  int count;

	  /* This is at worst case an O(n^2) algorithm, so limit our search
	     to the first 32 elements on the list.  This avoids trouble
	     compiling code with very long basic blocks that can easily
	     call simplify_gen_binary so many times that we run out of
	     memory.  */

	  found_better = 0;
	  for (p = elt->first_same_value, count = 0;
	       p && count < 32;
	       p = p->next_same_value, count++)
	    if (! p->flag
		&& (GET_CODE (p->exp) == REG
		    || exp_equiv_p (p->exp, p->exp, 1, 0)))
	      {
		rtx new = simplify_gen_binary (GET_CODE (*loc), Pmode,
					       p->exp, c);
		int new_cost;
		new_cost = address_cost (new, mode);

		if (new_cost < best_addr_cost
		    || (new_cost == best_addr_cost
			&& (COST (new) + 1) >> 1 > best_rtx_cost))
		  {
		    found_better = 1;
		    best_addr_cost = new_cost;
		    best_rtx_cost = (COST (new) + 1) >> 1;
		    best_elt = p;
		    best_rtx = new;
		  }
	      }

	  if (found_better)
	    {
	      if (validate_change (insn, loc,
				   canon_reg (copy_rtx (best_rtx),
					      NULL_RTX), 0))
		return;
	      else
		best_elt->flag = 1;
	    }
	}
    }
#endif
}

/* Given an operation (CODE, *PARG1, *PARG2), where code is a comparison
   operation (EQ, NE, GT, etc.), follow it back through the hash table and
   what values are being compared.

   *PARG1 and *PARG2 are updated to contain the rtx representing the values
   actually being compared.  For example, if *PARG1 was (cc0) and *PARG2
   was (const_int 0), *PARG1 and *PARG2 will be set to the objects that were
   compared to produce cc0.

   The return value is the comparison operator and is either the code of
   A or the code corresponding to the inverse of the comparison.  */

static enum rtx_code
find_comparison_args (code, parg1, parg2, pmode1, pmode2)
     enum rtx_code code;
     rtx *parg1, *parg2;
     enum machine_mode *pmode1, *pmode2;
{
  rtx arg1, arg2;

  arg1 = *parg1, arg2 = *parg2;

  /* If ARG2 is const0_rtx, see what ARG1 is equivalent to.  */

  while (arg2 == CONST0_RTX (GET_MODE (arg1)))
    {
      /* Set nonzero when we find something of interest.  */
      rtx x = 0;
      int reverse_code = 0;
      struct table_elt *p = 0;

      /* If arg1 is a COMPARE, extract the comparison arguments from it.
	 On machines with CC0, this is the only case that can occur, since
	 fold_rtx will return the COMPARE or item being compared with zero
	 when given CC0.  */

      if (GET_CODE (arg1) == COMPARE && arg2 == const0_rtx)
	x = arg1;

      /* If ARG1 is a comparison operator and CODE is testing for
	 STORE_FLAG_VALUE, get the inner arguments.  */

      else if (GET_RTX_CLASS (GET_CODE (arg1)) == '<')
	{
#ifdef FLOAT_STORE_FLAG_VALUE
	  REAL_VALUE_TYPE fsfv;
#endif

	  if (code == NE
	      || (GET_MODE_CLASS (GET_MODE (arg1)) == MODE_INT
		  && code == LT && STORE_FLAG_VALUE == -1)
#ifdef FLOAT_STORE_FLAG_VALUE
	      || (GET_MODE_CLASS (GET_MODE (arg1)) == MODE_FLOAT
		  && (fsfv = FLOAT_STORE_FLAG_VALUE (GET_MODE (arg1)),
		      REAL_VALUE_NEGATIVE (fsfv)))
#endif
	      )
	    x = arg1;
	  else if (code == EQ
		   || (GET_MODE_CLASS (GET_MODE (arg1)) == MODE_INT
		       && code == GE && STORE_FLAG_VALUE == -1)
#ifdef FLOAT_STORE_FLAG_VALUE
		   || (GET_MODE_CLASS (GET_MODE (arg1)) == MODE_FLOAT
		       && (fsfv = FLOAT_STORE_FLAG_VALUE (GET_MODE (arg1)),
			   REAL_VALUE_NEGATIVE (fsfv)))
#endif
		   )
	    x = arg1, reverse_code = 1;
	}

      /* ??? We could also check for

	 (ne (and (eq (...) (const_int 1))) (const_int 0))

	 and related forms, but let's wait until we see them occurring.  */

      if (x == 0)
	/* Look up ARG1 in the hash table and see if it has an equivalence
	   that lets us see what is being compared.  */
	p = lookup (arg1, safe_hash (arg1, GET_MODE (arg1)) & HASH_MASK,
		    GET_MODE (arg1));
      if (p)
	{
	  p = p->first_same_value;

	  /* If what we compare is already known to be constant, that is as
	     good as it gets.
	     We need to break the loop in this case, because otherwise we
	     can have an infinite loop when looking at a reg that is known
	     to be a constant which is the same as a comparison of a reg
	     against zero which appears later in the insn stream, which in
	     turn is constant and the same as the comparison of the first reg
	     against zero...  */
	  if (p->is_const)
	    break;
	}

      for (; p; p = p->next_same_value)
	{
	  enum machine_mode inner_mode = GET_MODE (p->exp);
#ifdef FLOAT_STORE_FLAG_VALUE
	  REAL_VALUE_TYPE fsfv;
#endif

	  /* If the entry isn't valid, skip it.  */
	  if (! exp_equiv_p (p->exp, p->exp, 1, 0))
	    continue;

	  if (GET_CODE (p->exp) == COMPARE
	      /* Another possibility is that this machine has a compare insn
		 that includes the comparison code.  In that case, ARG1 would
		 be equivalent to a comparison operation that would set ARG1 to
		 either STORE_FLAG_VALUE or zero.  If this is an NE operation,
		 ORIG_CODE is the actual comparison being done; if it is an EQ,
		 we must reverse ORIG_CODE.  On machine with a negative value
		 for STORE_FLAG_VALUE, also look at LT and GE operations.  */
	      || ((code == NE
		   || (code == LT
		       && GET_MODE_CLASS (inner_mode) == MODE_INT
		       && (GET_MODE_BITSIZE (inner_mode)
			   <= HOST_BITS_PER_WIDE_INT)
		       && (STORE_FLAG_VALUE
			   & ((HOST_WIDE_INT) 1
			      << (GET_MODE_BITSIZE (inner_mode) - 1))))
#ifdef FLOAT_STORE_FLAG_VALUE
		   || (code == LT
		       && GET_MODE_CLASS (inner_mode) == MODE_FLOAT
		       && (fsfv = FLOAT_STORE_FLAG_VALUE (GET_MODE (arg1)),
			   REAL_VALUE_NEGATIVE (fsfv)))
#endif
		   )
		  && GET_RTX_CLASS (GET_CODE (p->exp)) == '<'))
	    {
	      x = p->exp;
	      break;
	    }
	  else if ((code == EQ
		    || (code == GE
			&& GET_MODE_CLASS (inner_mode) == MODE_INT
			&& (GET_MODE_BITSIZE (inner_mode)
			    <= HOST_BITS_PER_WIDE_INT)
			&& (STORE_FLAG_VALUE
			    & ((HOST_WIDE_INT) 1
			       << (GET_MODE_BITSIZE (inner_mode) - 1))))
#ifdef FLOAT_STORE_FLAG_VALUE
		    || (code == GE
			&& GET_MODE_CLASS (inner_mode) == MODE_FLOAT
			&& (fsfv = FLOAT_STORE_FLAG_VALUE (GET_MODE (arg1)),
			    REAL_VALUE_NEGATIVE (fsfv)))
#endif
		    )
		   && GET_RTX_CLASS (GET_CODE (p->exp)) == '<')
	    {
	      reverse_code = 1;
	      x = p->exp;
	      break;
	    }

	  /* If this is fp + constant, the equivalent is a better operand since
	     it may let us predict the value of the comparison.  */
	  else if (NONZERO_BASE_PLUS_P (p->exp))
	    {
	      arg1 = p->exp;
	      continue;
	    }
	}

      /* If we didn't find a useful equivalence for ARG1, we are done.
	 Otherwise, set up for the next iteration.  */
      if (x == 0)
	break;

      /* If we need to reverse the comparison, make sure that that is
	 possible -- we can't necessarily infer the value of GE from LT
	 with floating-point operands.  */
      if (reverse_code)
	{
	  enum rtx_code reversed = reversed_comparison_code (x, NULL_RTX);
	  if (reversed == UNKNOWN)
	    break;
	  else
	    code = reversed;
	}
      else if (GET_RTX_CLASS (GET_CODE (x)) == '<')
	code = GET_CODE (x);
      arg1 = XEXP (x, 0), arg2 = XEXP (x, 1);
    }

  /* Return our results.  Return the modes from before fold_rtx
     because fold_rtx might produce const_int, and then it's too late.  */
  *pmode1 = GET_MODE (arg1), *pmode2 = GET_MODE (arg2);
  *parg1 = fold_rtx (arg1, 0), *parg2 = fold_rtx (arg2, 0);

  return code;
}

/* If X is a nontrivial arithmetic operation on an argument
   for which a constant value can be determined, return
   the result of operating on that value, as a constant.
   Otherwise, return X, possibly with one or more operands
   modified by recursive calls to this function.

   If X is a register whose contents are known, we do NOT
   return those contents here.  equiv_constant is called to
   perform that task.

   INSN is the insn that we may be modifying.  If it is 0, make a copy
   of X before modifying it.  */

static rtx
fold_rtx (x, insn)
     rtx x;
     rtx insn;
{
  enum rtx_code code;
  enum machine_mode mode;
  const char *fmt;
  int i;
  rtx new = 0;
  int copied = 0;
  int must_swap = 0;

  /* Folded equivalents of first two operands of X.  */
  rtx folded_arg0;
  rtx folded_arg1;

  /* Constant equivalents of first three operands of X;
     0 when no such equivalent is known.  */
  rtx const_arg0;
  rtx const_arg1;
  rtx const_arg2;

  /* The mode of the first operand of X.  We need this for sign and zero
     extends.  */
  enum machine_mode mode_arg0;

  if (x == 0)
    return x;

  mode = GET_MODE (x);
  code = GET_CODE (x);
  switch (code)
    {
    case CONST:
    case CONST_INT:
    case CONST_DOUBLE:
    case CONST_VECTOR:
    case SYMBOL_REF:
    case LABEL_REF:
    case REG:
      /* No use simplifying an EXPR_LIST
	 since they are used only for lists of args
	 in a function call's REG_EQUAL note.  */
    case EXPR_LIST:
      /* Changing anything inside an ADDRESSOF is incorrect; we don't
	 want to (e.g.,) make (addressof (const_int 0)) just because
	 the location is known to be zero.  */
    case ADDRESSOF:
      return x;

#ifdef HAVE_cc0
    case CC0:
      return prev_insn_cc0;
#endif

    case PC:
      /* If the next insn is a CODE_LABEL followed by a jump table,
	 PC's value is a LABEL_REF pointing to that label.  That
	 lets us fold switch statements on the VAX.  */
      if (insn && GET_CODE (insn) == JUMP_INSN)
	{
	  rtx next = next_nonnote_insn (insn);

	  if (next && GET_CODE (next) == CODE_LABEL
	      && NEXT_INSN (next) != 0
	      && GET_CODE (NEXT_INSN (next)) == JUMP_INSN
	      && (GET_CODE (PATTERN (NEXT_INSN (next))) == ADDR_VEC
		  || GET_CODE (PATTERN (NEXT_INSN (next))) == ADDR_DIFF_VEC))
	    return gen_rtx_LABEL_REF (Pmode, next);
	}
      break;

    case SUBREG:
      /* See if we previously assigned a constant value to this SUBREG.  */
      if ((new = lookup_as_function (x, CONST_INT)) != 0
	  || (new = lookup_as_function (x, CONST_DOUBLE)) != 0)
	return new;

      /* If this is a paradoxical SUBREG, we have no idea what value the
	 extra bits would have.  However, if the operand is equivalent
	 to a SUBREG whose operand is the same as our mode, and all the
	 modes are within a word, we can just use the inner operand
	 because these SUBREGs just say how to treat the register.

	 Similarly if we find an integer constant.  */

      if (GET_MODE_SIZE (mode) > GET_MODE_SIZE (GET_MODE (SUBREG_REG (x))))
	{
	  enum machine_mode imode = GET_MODE (SUBREG_REG (x));
	  struct table_elt *elt;

	  if (GET_MODE_SIZE (mode) <= UNITS_PER_WORD
	      && GET_MODE_SIZE (imode) <= UNITS_PER_WORD
	      && (elt = lookup (SUBREG_REG (x), HASH (SUBREG_REG (x), imode),
				imode)) != 0)
	    for (elt = elt->first_same_value; elt; elt = elt->next_same_value)
	      {
		if (CONSTANT_P (elt->exp)
		    && GET_MODE (elt->exp) == VOIDmode)
		  return elt->exp;

		if (GET_CODE (elt->exp) == SUBREG
		    && GET_MODE (SUBREG_REG (elt->exp)) == mode
		    && exp_equiv_p (elt->exp, elt->exp, 1, 0))
		  return copy_rtx (SUBREG_REG (elt->exp));
	      }

	  return x;
	}

      /* Fold SUBREG_REG.  If it changed, see if we can simplify the SUBREG.
	 We might be able to if the SUBREG is extracting a single word in an
	 integral mode or extracting the low part.  */

      folded_arg0 = fold_rtx (SUBREG_REG (x), insn);
      const_arg0 = equiv_constant (folded_arg0);
      if (const_arg0)
	folded_arg0 = const_arg0;

      if (folded_arg0 != SUBREG_REG (x))
	{
	  new = simplify_subreg (mode, folded_arg0,
				 GET_MODE (SUBREG_REG (x)), SUBREG_BYTE (x));
	  if (new)
	    return new;
	}

      /* If this is a narrowing SUBREG and our operand is a REG, see if
	 we can find an equivalence for REG that is an arithmetic operation
	 in a wider mode where both operands are paradoxical SUBREGs
	 from objects of our result mode.  In that case, we couldn't report
	 an equivalent value for that operation, since we don't know what the
	 extra bits will be.  But we can find an equivalence for this SUBREG
	 by folding that operation is the narrow mode.  This allows us to
	 fold arithmetic in narrow modes when the machine only supports
	 word-sized arithmetic.

	 Also look for a case where we have a SUBREG whose operand is the
	 same as our result.  If both modes are smaller than a word, we
	 are simply interpreting a register in different modes and we
	 can use the inner value.  */

      if (GET_CODE (folded_arg0) == REG
	  && GET_MODE_SIZE (mode) < GET_MODE_SIZE (GET_MODE (folded_arg0))
	  && subreg_lowpart_p (x))
	{
	  struct table_elt *elt;

	  /* We can use HASH here since we know that canon_hash won't be
	     called.  */
	  elt = lookup (folded_arg0,
			HASH (folded_arg0, GET_MODE (folded_arg0)),
			GET_MODE (folded_arg0));

	  if (elt)
	    elt = elt->first_same_value;

	  for (; elt; elt = elt->next_same_value)
	    {
	      enum rtx_code eltcode = GET_CODE (elt->exp);

	      /* Just check for unary and binary operations.  */
	      if (GET_RTX_CLASS (GET_CODE (elt->exp)) == '1'
		  && GET_CODE (elt->exp) != SIGN_EXTEND
		  && GET_CODE (elt->exp) != ZERO_EXTEND
		  && GET_CODE (XEXP (elt->exp, 0)) == SUBREG
		  && GET_MODE (SUBREG_REG (XEXP (elt->exp, 0))) == mode
		  && (GET_MODE_CLASS (mode)
		      == GET_MODE_CLASS (GET_MODE (XEXP (elt->exp, 0)))))
		{
		  rtx op0 = SUBREG_REG (XEXP (elt->exp, 0));

		  if (GET_CODE (op0) != REG && ! CONSTANT_P (op0))
		    op0 = fold_rtx (op0, NULL_RTX);

		  op0 = equiv_constant (op0);
		  if (op0)
		    new = simplify_unary_operation (GET_CODE (elt->exp), mode,
						    op0, mode);
		}
	      else if ((GET_RTX_CLASS (GET_CODE (elt->exp)) == '2'
			|| GET_RTX_CLASS (GET_CODE (elt->exp)) == 'c')
		       && eltcode != DIV && eltcode != MOD
		       && eltcode != UDIV && eltcode != UMOD
		       && eltcode != ASHIFTRT && eltcode != LSHIFTRT
		       && eltcode != ROTATE && eltcode != ROTATERT
		       && ((GET_CODE (XEXP (elt->exp, 0)) == SUBREG
			    && (GET_MODE (SUBREG_REG (XEXP (elt->exp, 0)))
				== mode))
			   || CONSTANT_P (XEXP (elt->exp, 0)))
		       && ((GET_CODE (XEXP (elt->exp, 1)) == SUBREG
			    && (GET_MODE (SUBREG_REG (XEXP (elt->exp, 1)))
				== mode))
			   || CONSTANT_P (XEXP (elt->exp, 1))))
		{
		  rtx op0 = gen_lowpart_common (mode, XEXP (elt->exp, 0));
		  rtx op1 = gen_lowpart_common (mode, XEXP (elt->exp, 1));

		  if (op0 && GET_CODE (op0) != REG && ! CONSTANT_P (op0))
		    op0 = fold_rtx (op0, NULL_RTX);

		  if (op0)
		    op0 = equiv_constant (op0);

		  if (op1 && GET_CODE (op1) != REG && ! CONSTANT_P (op1))
		    op1 = fold_rtx (op1, NULL_RTX);

		  if (op1)
		    op1 = equiv_constant (op1);

		  /* If we are looking for the low SImode part of
		     (ashift:DI c (const_int 32)), it doesn't work
		     to compute that in SImode, because a 32-bit shift
		     in SImode is unpredictable.  We know the value is 0.  */
		  if (op0 && op1
		      && GET_CODE (elt->exp) == ASHIFT
		      && GET_CODE (op1) == CONST_INT
		      && INTVAL (op1) >= GET_MODE_BITSIZE (mode))
		    {
		      if (INTVAL (op1) < GET_MODE_BITSIZE (GET_MODE (elt->exp)))

			/* If the count fits in the inner mode's width,
			   but exceeds the outer mode's width,
			   the value will get truncated to 0
			   by the subreg.  */
			new = const0_rtx;
		      else
			/* If the count exceeds even the inner mode's width,
			   don't fold this expression.  */
			new = 0;
		    }
		  else if (op0 && op1)
		    new = simplify_binary_operation (GET_CODE (elt->exp), mode,
						     op0, op1);
		}

	      else if (GET_CODE (elt->exp) == SUBREG
		       && GET_MODE (SUBREG_REG (elt->exp)) == mode
		       && (GET_MODE_SIZE (GET_MODE (folded_arg0))
			   <= UNITS_PER_WORD)
		       && exp_equiv_p (elt->exp, elt->exp, 1, 0))
		new = copy_rtx (SUBREG_REG (elt->exp));

	      if (new)
		return new;
	    }
	}

      return x;

    case NOT:
    case NEG:
      /* If we have (NOT Y), see if Y is known to be (NOT Z).
	 If so, (NOT Y) simplifies to Z.  Similarly for NEG.  */
      new = lookup_as_function (XEXP (x, 0), code);
      if (new)
	return fold_rtx (copy_rtx (XEXP (new, 0)), insn);
      break;

    case MEM:
      /* If we are not actually processing an insn, don't try to find the
	 best address.  Not only don't we care, but we could modify the
	 MEM in an invalid way since we have no insn to validate against.  */
      if (insn != 0)
	find_best_addr (insn, &XEXP (x, 0), GET_MODE (x));

      {
	/* Even if we don't fold in the insn itself,
	   we can safely do so here, in hopes of getting a constant.  */
	rtx addr = fold_rtx (XEXP (x, 0), NULL_RTX);
	rtx base = 0;
	HOST_WIDE_INT offset = 0;

	if (GET_CODE (addr) == REG
	    && REGNO_QTY_VALID_P (REGNO (addr)))
	  {
	    int addr_q = REG_QTY (REGNO (addr));
	    struct qty_table_elem *addr_ent = &qty_table[addr_q];

	    if (GET_MODE (addr) == addr_ent->mode
		&& addr_ent->const_rtx != NULL_RTX)
	      addr = addr_ent->const_rtx;
	  }

	/* If address is constant, split it into a base and integer offset.  */
	if (GET_CODE (addr) == SYMBOL_REF || GET_CODE (addr) == LABEL_REF)
	  base = addr;
	else if (GET_CODE (addr) == CONST && GET_CODE (XEXP (addr, 0)) == PLUS
		 && GET_CODE (XEXP (XEXP (addr, 0), 1)) == CONST_INT)
	  {
	    base = XEXP (XEXP (addr, 0), 0);
	    offset = INTVAL (XEXP (XEXP (addr, 0), 1));
	  }
	else if (GET_CODE (addr) == LO_SUM
		 && GET_CODE (XEXP (addr, 1)) == SYMBOL_REF)
	  base = XEXP (addr, 1);
	else if (GET_CODE (addr) == ADDRESSOF)
	  return change_address (x, VOIDmode, addr);

	/* If this is a constant pool reference, we can fold it into its
	   constant to allow better value tracking.  */
	if (base && GET_CODE (base) == SYMBOL_REF
	    && CONSTANT_POOL_ADDRESS_P (base))
	  {
	    rtx constant = get_pool_constant (base);
	    enum machine_mode const_mode = get_pool_mode (base);
	    rtx new;

	    if (CONSTANT_P (constant) && GET_CODE (constant) != CONST_INT)
	      constant_pool_entries_cost = COST (constant);

	    /* If we are loading the full constant, we have an equivalence.  */
	    if (offset == 0 && mode == const_mode)
	      return constant;

	    /* If this actually isn't a constant (weird!), we can't do
	       anything.  Otherwise, handle the two most common cases:
	       extracting a word from a multi-word constant, and extracting
	       the low-order bits.  Other cases don't seem common enough to
	       worry about.  */
	    if (! CONSTANT_P (constant))
	      return x;

	    if (GET_MODE_CLASS (mode) == MODE_INT
		&& GET_MODE_SIZE (mode) == UNITS_PER_WORD
		&& offset % UNITS_PER_WORD == 0
		&& (new = operand_subword (constant,
					   offset / UNITS_PER_WORD,
					   0, const_mode)) != 0)
	      return new;

	    if (((BYTES_BIG_ENDIAN
		  && offset == GET_MODE_SIZE (GET_MODE (constant)) - 1)
		 || (! BYTES_BIG_ENDIAN && offset == 0))
		&& (new = gen_lowpart_if_possible (mode, constant)) != 0)
	      return new;
	  }

	/* If this is a reference to a label at a known position in a jump
	   table, we also know its value.  */
	if (base && GET_CODE (base) == LABEL_REF)
	  {
	    rtx label = XEXP (base, 0);
	    rtx table_insn = NEXT_INSN (label);

	    if (table_insn && GET_CODE (table_insn) == JUMP_INSN
		&& GET_CODE (PATTERN (table_insn)) == ADDR_VEC)
	      {
		rtx table = PATTERN (table_insn);

		if (offset >= 0
		    && (offset / GET_MODE_SIZE (GET_MODE (table))
			< XVECLEN (table, 0)))
		  return XVECEXP (table, 0,
				  offset / GET_MODE_SIZE (GET_MODE (table)));
	      }
	    if (table_insn && GET_CODE (table_insn) == JUMP_INSN
		&& GET_CODE (PATTERN (table_insn)) == ADDR_DIFF_VEC)
	      {
		rtx table = PATTERN (table_insn);

		if (offset >= 0
		    && (offset / GET_MODE_SIZE (GET_MODE (table))
			< XVECLEN (table, 1)))
		  {
		    offset /= GET_MODE_SIZE (GET_MODE (table));
		    new = gen_rtx_MINUS (Pmode, XVECEXP (table, 1, offset),
					 XEXP (table, 0));

		    if (GET_MODE (table) != Pmode)
		      new = gen_rtx_TRUNCATE (GET_MODE (table), new);

		    /* Indicate this is a constant.  This isn't a
		       valid form of CONST, but it will only be used
		       to fold the next insns and then discarded, so
		       it should be safe.

		       Note this expression must be explicitly discarded,
		       by cse_insn, else it may end up in a REG_EQUAL note
		       and "escape" to cause problems elsewhere.  */
		    return gen_rtx_CONST (GET_MODE (new), new);
		  }
	      }
	  }

	return x;
      }

#ifdef NO_FUNCTION_CSE
    case CALL:
      if (CONSTANT_P (XEXP (XEXP (x, 0), 0)))
	return x;
      break;
#endif

    case ASM_OPERANDS:
      for (i = ASM_OPERANDS_INPUT_LENGTH (x) - 1; i >= 0; i--)
	validate_change (insn, &ASM_OPERANDS_INPUT (x, i),
			 fold_rtx (ASM_OPERANDS_INPUT (x, i), insn), 0);
      break;

    default:
      break;
    }

  const_arg0 = 0;
  const_arg1 = 0;
  const_arg2 = 0;
  mode_arg0 = VOIDmode;

  /* Try folding our operands.
     Then see which ones have constant values known.  */

  fmt = GET_RTX_FORMAT (code);
  for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
    if (fmt[i] == 'e')
      {
	rtx arg = XEXP (x, i);
	rtx folded_arg = arg, const_arg = 0;
	enum machine_mode mode_arg = GET_MODE (arg);
	rtx cheap_arg, expensive_arg;
	rtx replacements[2];
	int j;
	int old_cost = COST_IN (XEXP (x, i), code);

	/* Most arguments are cheap, so handle them specially.  */
	switch (GET_CODE (arg))
	  {
	  case REG:
	    /* This is the same as calling equiv_constant; it is duplicated
	       here for speed.  */
	    if (REGNO_QTY_VALID_P (REGNO (arg)))
	      {
		int arg_q = REG_QTY (REGNO (arg));
		struct qty_table_elem *arg_ent = &qty_table[arg_q];

		if (arg_ent->const_rtx != NULL_RTX
		    && GET_CODE (arg_ent->const_rtx) != REG
		    && GET_CODE (arg_ent->const_rtx) != PLUS)
		  const_arg
		    = gen_lowpart_if_possible (GET_MODE (arg),
					       arg_ent->const_rtx);
	      }
	    break;

	  case CONST:
	  case CONST_INT:
	  case SYMBOL_REF:
	  case LABEL_REF:
	  case CONST_DOUBLE:
	  case CONST_VECTOR:
	    const_arg = arg;
	    break;

#ifdef HAVE_cc0
	  case CC0:
	    folded_arg = prev_insn_cc0;
	    mode_arg = prev_insn_cc0_mode;
	    const_arg = equiv_constant (folded_arg);
	    break;
#endif

	  default:
	    folded_arg = fold_rtx (arg, insn);
	    const_arg = equiv_constant (folded_arg);
	  }

	/* For the first three operands, see if the operand
	   is constant or equivalent to a constant.  */
	switch (i)
	  {
	  case 0:
	    folded_arg0 = folded_arg;
	    const_arg0 = const_arg;
	    mode_arg0 = mode_arg;
	    break;
	  case 1:
	    folded_arg1 = folded_arg;
	    const_arg1 = const_arg;
	    break;
	  case 2:
	    const_arg2 = const_arg;
	    break;
	  }

	/* Pick the least expensive of the folded argument and an
	   equivalent constant argument.  */
	if (const_arg == 0 || const_arg == folded_arg
	    || COST_IN (const_arg, code) > COST_IN (folded_arg, code))
	  cheap_arg = folded_arg, expensive_arg = const_arg;
	else
	  cheap_arg = const_arg, expensive_arg = folded_arg;

	/* Try to replace the operand with the cheapest of the two
	   possibilities.  If it doesn't work and this is either of the first
	   two operands of a commutative operation, try swapping them.
	   If THAT fails, try the more expensive, provided it is cheaper
	   than what is already there.  */

	if (cheap_arg == XEXP (x, i))
	  continue;

	if (insn == 0 && ! copied)
	  {
	    x = copy_rtx (x);
	    copied = 1;
	  }

	/* Order the replacements from cheapest to most expensive.  */
	replacements[0] = cheap_arg;
	replacements[1] = expensive_arg;

	for (j = 0; j < 2 && replacements[j]; j++)
	  {
	    int new_cost = COST_IN (replacements[j], code);

	    /* Stop if what existed before was cheaper.  Prefer constants
	       in the case of a tie.  */
	    if (new_cost > old_cost
		|| (new_cost == old_cost && CONSTANT_P (XEXP (x, i))))
	      break;

	    /* It's not safe to substitute the operand of a conversion
	       operator with a constant, as the conversion's identity
	       depends upon the mode of it's operand.  This optimization
	       is handled by the call to simplify_unary_operation.  */
	    if (GET_RTX_CLASS (code) == '1'
		&& GET_MODE (replacements[j]) != mode_arg0
		&& (code == ZERO_EXTEND
		    || code == SIGN_EXTEND
		    || code == TRUNCATE
		    || code == FLOAT_TRUNCATE
		    || code == FLOAT_EXTEND
		    || code == FLOAT
		    || code == FIX
		    || code == UNSIGNED_FLOAT
		    || code == UNSIGNED_FIX))
	      continue;

	    if (validate_change (insn, &XEXP (x, i), replacements[j], 0))
	      break;

	    if (code == NE || code == EQ || GET_RTX_CLASS (code) == 'c'
		|| code == LTGT || code == UNEQ || code == ORDERED
		|| code == UNORDERED)
	      {
		validate_change (insn, &XEXP (x, i), XEXP (x, 1 - i), 1);
		validate_change (insn, &XEXP (x, 1 - i), replacements[j], 1);

		if (apply_change_group ())
		  {
		    /* Swap them back to be invalid so that this loop can
		       continue and flag them to be swapped back later.  */
		    rtx tem;

		    tem = XEXP (x, 0); XEXP (x, 0) = XEXP (x, 1);
				       XEXP (x, 1) = tem;
		    must_swap = 1;
		    break;
		  }
	      }
	  }
      }

    else
      {
	if (fmt[i] == 'E')
	  /* Don't try to fold inside of a vector of expressions.
	     Doing nothing is harmless.  */
	  {;}
      }

  /* If a commutative operation, place a constant integer as the second
     operand unless the first operand is also a constant integer.  Otherwise,
     place any constant second unless the first operand is also a constant.  */

  if (code == EQ || code == NE || GET_RTX_CLASS (code) == 'c'
      || code == LTGT || code == UNEQ || code == ORDERED
      || code == UNORDERED)
    {
      if (must_swap || (const_arg0
	  		&& (const_arg1 == 0
	      		    || (GET_CODE (const_arg0) == CONST_INT
			        && GET_CODE (const_arg1) != CONST_INT))))
	{
	  rtx tem = XEXP (x, 0);

	  if (insn == 0 && ! copied)
	    {
	      x = copy_rtx (x);
	      copied = 1;
	    }

	  validate_change (insn, &XEXP (x, 0), XEXP (x, 1), 1);
	  validate_change (insn, &XEXP (x, 1), tem, 1);
	  if (apply_change_group ())
	    {
	      tem = const_arg0, const_arg0 = const_arg1, const_arg1 = tem;
	      tem = folded_arg0, folded_arg0 = folded_arg1, folded_arg1 = tem;
	    }
	}
    }

  /* If X is an arithmetic operation, see if we can simplify it.  */

  switch (GET_RTX_CLASS (code))
    {
    case '1':
      {
	int is_const = 0;

	/* We can't simplify extension ops unless we know the
	   original mode.  */
	if ((code == ZERO_EXTEND || code == SIGN_EXTEND)
	    && mode_arg0 == VOIDmode)
	  break;

	/* If we had a CONST, strip it off and put it back later if we
	   fold.  */
	if (const_arg0 != 0 && GET_CODE (const_arg0) == CONST)
	  is_const = 1, const_arg0 = XEXP (const_arg0, 0);

	new = simplify_unary_operation (code, mode,
					const_arg0 ? const_arg0 : folded_arg0,
					mode_arg0);
	if (new != 0 && is_const)
	  new = gen_rtx_CONST (mode, new);
      }
      break;

    case '<':
      /* See what items are actually being compared and set FOLDED_ARG[01]
	 to those values and CODE to the actual comparison code.  If any are
	 constant, set CONST_ARG0 and CONST_ARG1 appropriately.  We needn't
	 do anything if both operands are already known to be constant.  */

      if (const_arg0 == 0 || const_arg1 == 0)
	{
	  struct table_elt *p0, *p1;
	  rtx true_rtx = const_true_rtx, false_rtx = const0_rtx;
	  enum machine_mode mode_arg1;

#ifdef FLOAT_STORE_FLAG_VALUE
	  if (GET_MODE_CLASS (mode) == MODE_FLOAT)
	    {
	      true_rtx = (CONST_DOUBLE_FROM_REAL_VALUE
			  (FLOAT_STORE_FLAG_VALUE (mode), mode));
	      false_rtx = CONST0_RTX (mode);
	    }
#endif

	  code = find_comparison_args (code, &folded_arg0, &folded_arg1,
				       &mode_arg0, &mode_arg1);
	  const_arg0 = equiv_constant (folded_arg0);
	  const_arg1 = equiv_constant (folded_arg1);

	  /* If the mode is VOIDmode or a MODE_CC mode, we don't know
	     what kinds of things are being compared, so we can't do
	     anything with this comparison.  */

	  if (mode_arg0 == VOIDmode || GET_MODE_CLASS (mode_arg0) == MODE_CC)
	    break;

	  /* If we do not now have two constants being compared, see
	     if we can nevertheless deduce some things about the
	     comparison.  */
	  if (const_arg0 == 0 || const_arg1 == 0)
	    {
	      /* Is FOLDED_ARG0 frame-pointer plus a constant?  Or
		 non-explicit constant?  These aren't zero, but we
		 don't know their sign.  */
	      if (const_arg1 == const0_rtx
		  && (NONZERO_BASE_PLUS_P (folded_arg0)
#if 0  /* Sad to say, on sysvr4, #pragma weak can make a symbol address
	  come out as 0.  */
		      || GET_CODE (folded_arg0) == SYMBOL_REF
#endif
		      || GET_CODE (folded_arg0) == LABEL_REF
		      || GET_CODE (folded_arg0) == CONST))
		{
		  if (code == EQ)
		    return false_rtx;
		  else if (code == NE)
		    return true_rtx;
		}

	      /* See if the two operands are the same.  */

	      if (folded_arg0 == folded_arg1
		  || (GET_CODE (folded_arg0) == REG
		      && GET_CODE (folded_arg1) == REG
		      && (REG_QTY (REGNO (folded_arg0))
			  == REG_QTY (REGNO (folded_arg1))))
		  || ((p0 = lookup (folded_arg0,
				    (safe_hash (folded_arg0, mode_arg0)
				     & HASH_MASK), mode_arg0))
		      && (p1 = lookup (folded_arg1,
				       (safe_hash (folded_arg1, mode_arg0)
					& HASH_MASK), mode_arg0))
		      && p0->first_same_value == p1->first_same_value))
		{
		  /* Sadly two equal NaNs are not equivalent.  */
		  if (!HONOR_NANS (mode_arg0))
		    return ((code == EQ || code == LE || code == GE
			     || code == LEU || code == GEU || code == UNEQ
			     || code == UNLE || code == UNGE
			     || code == ORDERED)
			    ? true_rtx : false_rtx);
		  /* Take care for the FP compares we can resolve.  */
		  if (code == UNEQ || code == UNLE || code == UNGE)
		    return true_rtx;
		  if (code == LTGT || code == LT || code == GT)
		    return false_rtx;
		}

	      /* If FOLDED_ARG0 is a register, see if the comparison we are
		 doing now is either the same as we did before or the reverse
		 (we only check the reverse if not floating-point).  */
	      else if (GET_CODE (folded_arg0) == REG)
		{
		  int qty = REG_QTY (REGNO (folded_arg0));

		  if (REGNO_QTY_VALID_P (REGNO (folded_arg0)))
		    {
		      struct qty_table_elem *ent = &qty_table[qty];

		      if ((comparison_dominates_p (ent->comparison_code, code)
			   || (! FLOAT_MODE_P (mode_arg0)
			       && comparison_dominates_p (ent->comparison_code,
						          reverse_condition (code))))
			  && (rtx_equal_p (ent->comparison_const, folded_arg1)
			      || (const_arg1
				  && rtx_equal_p (ent->comparison_const,
						  const_arg1))
			      || (GET_CODE (folded_arg1) == REG
				  && (REG_QTY (REGNO (folded_arg1)) == ent->comparison_qty))))
			return (comparison_dominates_p (ent->comparison_code, code)
				? true_rtx : false_rtx);
		    }
		}
	    }
	}

      /* If we are comparing against zero, see if the first operand is
	 equivalent to an IOR with a constant.  If so, we may be able to
	 determine the result of this comparison.  */

      if (const_arg1 == const0_rtx)
	{
	  rtx y = lookup_as_function (folded_arg0, IOR);
	  rtx inner_const;

	  if (y != 0
	      && (inner_const = equiv_constant (XEXP (y, 1))) != 0
	      && GET_CODE (inner_const) == CONST_INT
	      && INTVAL (inner_const) != 0)
	    {
	      int sign_bitnum = GET_MODE_BITSIZE (mode_arg0) - 1;
	      int has_sign = (HOST_BITS_PER_WIDE_INT >= sign_bitnum
			      && (INTVAL (inner_const)
				  & ((HOST_WIDE_INT) 1 << sign_bitnum)));
	      rtx true_rtx = const_true_rtx, false_rtx = const0_rtx;

#ifdef FLOAT_STORE_FLAG_VALUE
	      if (GET_MODE_CLASS (mode) == MODE_FLOAT)
		{
		  true_rtx = (CONST_DOUBLE_FROM_REAL_VALUE
			  (FLOAT_STORE_FLAG_VALUE (mode), mode));
		  false_rtx = CONST0_RTX (mode);
		}
#endif

	      switch (code)
		{
		case EQ:
		  return false_rtx;
		case NE:
		  return true_rtx;
		case LT:  case LE:
		  if (has_sign)
		    return true_rtx;
		  break;
		case GT:  case GE:
		  if (has_sign)
		    return false_rtx;
		  break;
		default:
		  break;
		}
	    }
	}

      new = simplify_relational_operation (code,
					   (mode_arg0 != VOIDmode
					    ? mode_arg0
					    : (GET_MODE (const_arg0
							 ? const_arg0
							 : folded_arg0)
					       != VOIDmode)
					    ? GET_MODE (const_arg0
							? const_arg0
							: folded_arg0)
					    : GET_MODE (const_arg1
							? const_arg1
							: folded_arg1)),
					   const_arg0 ? const_arg0 : folded_arg0,
					   const_arg1 ? const_arg1 : folded_arg1);
#ifdef FLOAT_STORE_FLAG_VALUE
      if (new != 0 && GET_MODE_CLASS (mode) == MODE_FLOAT)
	{
	  if (new == const0_rtx)
	    new = CONST0_RTX (mode);
	  else
	    new = (CONST_DOUBLE_FROM_REAL_VALUE
		   (FLOAT_STORE_FLAG_VALUE (mode), mode));
	}
#endif
      break;

    case '2':
    case 'c':
      switch (code)
	{
	case PLUS:
	  /* If the second operand is a LABEL_REF, see if the first is a MINUS
	     with that LABEL_REF as its second operand.  If so, the result is
	     the first operand of that MINUS.  This handles switches with an
	     ADDR_DIFF_VEC table.  */
	  if (const_arg1 && GET_CODE (const_arg1) == LABEL_REF)
	    {
	      rtx y
		= GET_CODE (folded_arg0) == MINUS ? folded_arg0
		: lookup_as_function (folded_arg0, MINUS);

	      if (y != 0 && GET_CODE (XEXP (y, 1)) == LABEL_REF
		  && XEXP (XEXP (y, 1), 0) == XEXP (const_arg1, 0))
		return XEXP (y, 0);

	      /* Now try for a CONST of a MINUS like the above.  */
	      if ((y = (GET_CODE (folded_arg0) == CONST ? folded_arg0
			: lookup_as_function (folded_arg0, CONST))) != 0
		  && GET_CODE (XEXP (y, 0)) == MINUS
		  && GET_CODE (XEXP (XEXP (y, 0), 1)) == LABEL_REF
		  && XEXP (XEXP (XEXP (y, 0), 1), 0) == XEXP (const_arg1, 0))
		return XEXP (XEXP (y, 0), 0);
	    }

	  /* Likewise if the operands are in the other order.  */
	  if (const_arg0 && GET_CODE (const_arg0) == LABEL_REF)
	    {
	      rtx y
		= GET_CODE (folded_arg1) == MINUS ? folded_arg1
		: lookup_as_function (folded_arg1, MINUS);

	      if (y != 0 && GET_CODE (XEXP (y, 1)) == LABEL_REF
		  && XEXP (XEXP (y, 1), 0) == XEXP (const_arg0, 0))
		return XEXP (y, 0);

	      /* Now try for a CONST of a MINUS like the above.  */
	      if ((y = (GET_CODE (folded_arg1) == CONST ? folded_arg1
			: lookup_as_function (folded_arg1, CONST))) != 0
		  && GET_CODE (XEXP (y, 0)) == MINUS
		  && GET_CODE (XEXP (XEXP (y, 0), 1)) == LABEL_REF
		  && XEXP (XEXP (XEXP (y, 0), 1), 0) == XEXP (const_arg0, 0))
		return XEXP (XEXP (y, 0), 0);
	    }

	  /* If second operand is a register equivalent to a negative
	     CONST_INT, see if we can find a register equivalent to the
	     positive constant.  Make a MINUS if so.  Don't do this for
	     a non-negative constant since we might then alternate between
	     choosing positive and negative constants.  Having the positive
	     constant previously-used is the more common case.  Be sure
	     the resulting constant is non-negative; if const_arg1 were
	     the smallest negative number this would overflow: depending
	     on the mode, this would either just be the same value (and
	     hence not save anything) or be incorrect.  */
	  if (const_arg1 != 0 && GET_CODE (const_arg1) == CONST_INT
	      && INTVAL (const_arg1) < 0
	      /* This used to test

	         -INTVAL (const_arg1) >= 0

		 But The Sun V5.0 compilers mis-compiled that test.  So
		 instead we test for the problematic value in a more direct
		 manner and hope the Sun compilers get it correct.  */
	      && INTVAL (const_arg1) !=
	        ((HOST_WIDE_INT) 1 << (HOST_BITS_PER_WIDE_INT - 1))
	      && GET_CODE (folded_arg1) == REG)
	    {
	      rtx new_const = GEN_INT (-INTVAL (const_arg1));
	      struct table_elt *p
		= lookup (new_const, safe_hash (new_const, mode) & HASH_MASK,
			  mode);

	      if (p)
		for (p = p->first_same_value; p; p = p->next_same_value)
		  if (GET_CODE (p->exp) == REG)
		    return simplify_gen_binary (MINUS, mode, folded_arg0,
						canon_reg (p->exp, NULL_RTX));
	    }
	  goto from_plus;

	case MINUS:
	  /* If we have (MINUS Y C), see if Y is known to be (PLUS Z C2).
	     If so, produce (PLUS Z C2-C).  */
	  if (const_arg1 != 0 && GET_CODE (const_arg1) == CONST_INT)
	    {
	      rtx y = lookup_as_function (XEXP (x, 0), PLUS);
	      if (y && GET_CODE (XEXP (y, 1)) == CONST_INT)
		return fold_rtx (plus_constant (copy_rtx (y),
						-INTVAL (const_arg1)),
				 NULL_RTX);
	    }

	  /* Fall through.  */

	from_plus:
	case SMIN:    case SMAX:      case UMIN:    case UMAX:
	case IOR:     case AND:       case XOR:
	case MULT:
	case ASHIFT:  case LSHIFTRT:  case ASHIFTRT:
	  /* If we have (<op> <reg> <const_int>) for an associative OP and REG
	     is known to be of similar form, we may be able to replace the
	     operation with a combined operation.  This may eliminate the
	     intermediate operation if every use is simplified in this way.
	     Note that the similar optimization done by combine.c only works
	     if the intermediate operation's result has only one reference.  */

	  if (GET_CODE (folded_arg0) == REG
	      && const_arg1 && GET_CODE (const_arg1) == CONST_INT)
	    {
	      int is_shift
		= (code == ASHIFT || code == ASHIFTRT || code == LSHIFTRT);
	      rtx y = lookup_as_function (folded_arg0, code);
	      rtx inner_const;
	      enum rtx_code associate_code;
	      rtx new_const;

	      if (y == 0
		  || 0 == (inner_const
			   = equiv_constant (fold_rtx (XEXP (y, 1), 0)))
		  || GET_CODE (inner_const) != CONST_INT
		  /* If we have compiled a statement like
		     "if (x == (x & mask1))", and now are looking at
		     "x & mask2", we will have a case where the first operand
		     of Y is the same as our first operand.  Unless we detect
		     this case, an infinite loop will result.  */
		  || XEXP (y, 0) == folded_arg0)
		break;

	      /* Don't associate these operations if they are a PLUS with the
		 same constant and it is a power of two.  These might be doable
		 with a pre- or post-increment.  Similarly for two subtracts of
		 identical powers of two with post decrement.  */

	      if (code == PLUS && INTVAL (const_arg1) == INTVAL (inner_const)
		  && ((HAVE_PRE_INCREMENT
			  && exact_log2 (INTVAL (const_arg1)) >= 0)
		      || (HAVE_POST_INCREMENT
			  && exact_log2 (INTVAL (const_arg1)) >= 0)
		      || (HAVE_PRE_DECREMENT
			  && exact_log2 (- INTVAL (const_arg1)) >= 0)
		      || (HAVE_POST_DECREMENT
			  && exact_log2 (- INTVAL (const_arg1)) >= 0)))
		break;

	      /* Compute the code used to compose the constants.  For example,
		 A-C1-C2 is A-(C1 + C2), so if CODE == MINUS, we want PLUS.  */

	      associate_code = (is_shift || code == MINUS ? PLUS : code);

	      new_const = simplify_binary_operation (associate_code, mode,
						     const_arg1, inner_const);

	      if (new_const == 0)
		break;

	      /* If we are associating shift operations, don't let this
		 produce a shift of the size of the object or larger.
		 This could occur when we follow a sign-extend by a right
		 shift on a machine that does a sign-extend as a pair
		 of shifts.  */

	      if (is_shift && GET_CODE (new_const) == CONST_INT
		  && INTVAL (new_const) >= GET_MODE_BITSIZE (mode))
		{
		  /* As an exception, we can turn an ASHIFTRT of this
		     form into a shift of the number of bits - 1.  */
		  if (code == ASHIFTRT)
		    new_const = GEN_INT (GET_MODE_BITSIZE (mode) - 1);
		  else
		    break;
		}

	      y = copy_rtx (XEXP (y, 0));

	      /* If Y contains our first operand (the most common way this
		 can happen is if Y is a MEM), we would do into an infinite
		 loop if we tried to fold it.  So don't in that case.  */

	      if (! reg_mentioned_p (folded_arg0, y))
		y = fold_rtx (y, insn);

	      return simplify_gen_binary (code, mode, y, new_const);
	    }
	  break;

	case DIV:       case UDIV:
	  /* ??? The associative optimization performed immediately above is
	     also possible for DIV and UDIV using associate_code of MULT.
	     However, we would need extra code to verify that the
	     multiplication does not overflow, that is, there is no overflow
	     in the calculation of new_const.  */
	  break;

	default:
	  break;
	}

      new = simplify_binary_operation (code, mode,
				       const_arg0 ? const_arg0 : folded_arg0,
				       const_arg1 ? const_arg1 : folded_arg1);
      break;

    case 'o':
      /* (lo_sum (high X) X) is simply X.  */
      if (code == LO_SUM && const_arg0 != 0
	  && GET_CODE (const_arg0) == HIGH
	  && rtx_equal_p (XEXP (const_arg0, 0), const_arg1))
	return const_arg1;
      break;

    case '3':
    case 'b':
      new = simplify_ternary_operation (code, mode, mode_arg0,
					const_arg0 ? const_arg0 : folded_arg0,
					const_arg1 ? const_arg1 : folded_arg1,
					const_arg2 ? const_arg2 : XEXP (x, 2));
      break;

    case 'x':
      /* Always eliminate CONSTANT_P_RTX at this stage.  */
      if (code == CONSTANT_P_RTX)
	return (const_arg0 ? const1_rtx : const0_rtx);
      break;
    }

  return new ? new : x;
}

/* Return a constant value currently equivalent to X.
   Return 0 if we don't know one.  */

static rtx
equiv_constant (x)
     rtx x;
{
  if (GET_CODE (x) == REG
      && REGNO_QTY_VALID_P (REGNO (x)))
    {
      int x_q = REG_QTY (REGNO (x));
      struct qty_table_elem *x_ent = &qty_table[x_q];

      if (x_ent->const_rtx)
	x = gen_lowpart_if_possible (GET_MODE (x), x_ent->const_rtx);
    }

  if (x == 0 || CONSTANT_P (x))
    return x;

  /* If X is a MEM, try to fold it outside the context of any insn to see if
     it might be equivalent to a constant.  That handles the case where it
     is a constant-pool reference.  Then try to look it up in the hash table
     in case it is something whose value we have seen before.  */

  if (GET_CODE (x) == MEM)
    {
      struct table_elt *elt;

      x = fold_rtx (x, NULL_RTX);
      if (CONSTANT_P (x))
	return x;

      elt = lookup (x, safe_hash (x, GET_MODE (x)) & HASH_MASK, GET_MODE (x));
      if (elt == 0)
	return 0;

      for (elt = elt->first_same_value; elt; elt = elt->next_same_value)
	if (elt->is_const && CONSTANT_P (elt->exp))
	  return elt->exp;
    }

  return 0;
}

/* Assuming that X is an rtx (e.g., MEM, REG or SUBREG) for a fixed-point
   number, return an rtx (MEM, SUBREG, or CONST_INT) that refers to the
   least-significant part of X.
   MODE specifies how big a part of X to return.

   If the requested operation cannot be done, 0 is returned.

   This is similar to gen_lowpart in emit-rtl.c.  */

rtx
gen_lowpart_if_possible (mode, x)
     enum machine_mode mode;
     rtx x;
{
  rtx result = gen_lowpart_common (mode, x);

  if (result)
    return result;
  else if (GET_CODE (x) == MEM)
    {
      /* This is the only other case we handle.  */
      int offset = 0;
      rtx new;

      if (WORDS_BIG_ENDIAN)
	offset = (MAX (GET_MODE_SIZE (GET_MODE (x)), UNITS_PER_WORD)
		  - MAX (GET_MODE_SIZE (mode), UNITS_PER_WORD));
      if (BYTES_BIG_ENDIAN)
	/* Adjust the address so that the address-after-the-data is
	   unchanged.  */
	offset -= (MIN (UNITS_PER_WORD, GET_MODE_SIZE (mode))
		   - MIN (UNITS_PER_WORD, GET_MODE_SIZE (GET_MODE (x))));

      new = adjust_address_nv (x, mode, offset);
      if (! memory_address_p (mode, XEXP (new, 0)))
	return 0;

      return new;
    }
  else
    return 0;
}

/* Given INSN, a jump insn, TAKEN indicates if we are following the "taken"
   branch.  It will be zero if not.

   In certain cases, this can cause us to add an equivalence.  For example,
   if we are following the taken case of
   	if (i == 2)
   we can add the fact that `i' and '2' are now equivalent.

   In any case, we can record that this comparison was passed.  If the same
   comparison is seen later, we will know its value.  */

static void
record_jump_equiv (insn, taken)
     rtx insn;
     int taken;
{
  int cond_known_true;
  rtx op0, op1;
  rtx set;
  enum machine_mode mode, mode0, mode1;
  int reversed_nonequality = 0;
  enum rtx_code code;

  /* Ensure this is the right kind of insn.  */
  if (! any_condjump_p (insn))
    return;
  set = pc_set (insn);

  /* See if this jump condition is known true or false.  */
  if (taken)
    cond_known_true = (XEXP (SET_SRC (set), 2) == pc_rtx);
  else
    cond_known_true = (XEXP (SET_SRC (set), 1) == pc_rtx);

  /* Get the type of comparison being done and the operands being compared.
     If we had to reverse a non-equality condition, record that fact so we
     know that it isn't valid for floating-point.  */
  code = GET_CODE (XEXP (SET_SRC (set), 0));
  op0 = fold_rtx (XEXP (XEXP (SET_SRC (set), 0), 0), insn);
  op1 = fold_rtx (XEXP (XEXP (SET_SRC (set), 0), 1), insn);

  code = find_comparison_args (code, &op0, &op1, &mode0, &mode1);
  if (! cond_known_true)
    {
      code = reversed_comparison_code_parts (code, op0, op1, insn);

      /* Don't remember if we can't find the inverse.  */
      if (code == UNKNOWN)
	return;
    }

  /* The mode is the mode of the non-constant.  */
  mode = mode0;
  if (mode1 != VOIDmode)
    mode = mode1;

  record_jump_cond (code, mode, op0, op1, reversed_nonequality);
}

/* We know that comparison CODE applied to OP0 and OP1 in MODE is true.
   REVERSED_NONEQUALITY is nonzero if CODE had to be swapped.
   Make any useful entries we can with that information.  Called from
   above function and called recursively.  */

static void
record_jump_cond (code, mode, op0, op1, reversed_nonequality)
     enum rtx_code code;
     enum machine_mode mode;
     rtx op0, op1;
     int reversed_nonequality;
{
  unsigned op0_hash, op1_hash;
  int op0_in_memory, op1_in_memory;
  struct table_elt *op0_elt, *op1_elt;

  /* If OP0 and OP1 are known equal, and either is a paradoxical SUBREG,
     we know that they are also equal in the smaller mode (this is also
     true for all smaller modes whether or not there is a SUBREG, but
     is not worth testing for with no SUBREG).  */

  /* Note that GET_MODE (op0) may not equal MODE.  */
  if (code == EQ && GET_CODE (op0) == SUBREG
      && (GET_MODE_SIZE (GET_MODE (op0))
	  > GET_MODE_SIZE (GET_MODE (SUBREG_REG (op0)))))
    {
      enum machine_mode inner_mode = GET_MODE (SUBREG_REG (op0));
      rtx tem = gen_lowpart_if_possible (inner_mode, op1);

      record_jump_cond (code, mode, SUBREG_REG (op0),
			tem ? tem : gen_rtx_SUBREG (inner_mode, op1, 0),
			reversed_nonequality);
    }

  if (code == EQ && GET_CODE (op1) == SUBREG
      && (GET_MODE_SIZE (GET_MODE (op1))
	  > GET_MODE_SIZE (GET_MODE (SUBREG_REG (op1)))))
    {
      enum machine_mode inner_mode = GET_MODE (SUBREG_REG (op1));
      rtx tem = gen_lowpart_if_possible (inner_mode, op0);

      record_jump_cond (code, mode, SUBREG_REG (op1),
			tem ? tem : gen_rtx_SUBREG (inner_mode, op0, 0),
			reversed_nonequality);
    }

  /* Similarly, if this is an NE comparison, and either is a SUBREG
     making a smaller mode, we know the whole thing is also NE.  */

  /* Note that GET_MODE (op0) may not equal MODE;
     if we test MODE instead, we can get an infinite recursion
     alternating between two modes each wider than MODE.  */

  if (code == NE && GET_CODE (op0) == SUBREG
      && subreg_lowpart_p (op0)
      && (GET_MODE_SIZE (GET_MODE (op0))
	  < GET_MODE_SIZE (GET_MODE (SUBREG_REG (op0)))))
    {
      enum machine_mode inner_mode = GET_MODE (SUBREG_REG (op0));
      rtx tem = gen_lowpart_if_possible (inner_mode, op1);

      record_jump_cond (code, mode, SUBREG_REG (op0),
			tem ? tem : gen_rtx_SUBREG (inner_mode, op1, 0),
			reversed_nonequality);
    }

  if (code == NE && GET_CODE (op1) == SUBREG
      && subreg_lowpart_p (op1)
      && (GET_MODE_SIZE (GET_MODE (op1))
	  < GET_MODE_SIZE (GET_MODE (SUBREG_REG (op1)))))
    {
      enum machine_mode inner_mode = GET_MODE (SUBREG_REG (op1));
      rtx tem = gen_lowpart_if_possible (inner_mode, op0);

      record_jump_cond (code, mode, SUBREG_REG (op1),
			tem ? tem : gen_rtx_SUBREG (inner_mode, op0, 0),
			reversed_nonequality);
    }

  /* Hash both operands.  */

  do_not_record = 0;
  hash_arg_in_memory = 0;
  op0_hash = HASH (op0, mode);
  op0_in_memory = hash_arg_in_memory;

  if (do_not_record)
    return;

  do_not_record = 0;
  hash_arg_in_memory = 0;
  op1_hash = HASH (op1, mode);
  op1_in_memory = hash_arg_in_memory;

  if (do_not_record)
    return;

  /* Look up both operands.  */
  op0_elt = lookup (op0, op0_hash, mode);
  op1_elt = lookup (op1, op1_hash, mode);

  /* If both operands are already equivalent or if they are not in the
     table but are identical, do nothing.  */
  if ((op0_elt != 0 && op1_elt != 0
       && op0_elt->first_same_value == op1_elt->first_same_value)
      || op0 == op1 || rtx_equal_p (op0, op1))
    return;

  /* If we aren't setting two things equal all we can do is save this
     comparison.   Similarly if this is floating-point.  In the latter
     case, OP1 might be zero and both -0.0 and 0.0 are equal to it.
     If we record the equality, we might inadvertently delete code
     whose intent was to change -0 to +0.  */

  if (code != EQ || FLOAT_MODE_P (GET_MODE (op0)))
    {
      struct qty_table_elem *ent;
      int qty;

      /* If we reversed a floating-point comparison, if OP0 is not a
	 register, or if OP1 is neither a register or constant, we can't
	 do anything.  */

      if (GET_CODE (op1) != REG)
	op1 = equiv_constant (op1);

      if ((reversed_nonequality && FLOAT_MODE_P (mode))
	  || GET_CODE (op0) != REG || op1 == 0)
	return;

      /* Put OP0 in the hash table if it isn't already.  This gives it a
	 new quantity number.  */
      if (op0_elt == 0)
	{
	  if (insert_regs (op0, NULL, 0))
	    {
	      rehash_using_reg (op0);
	      op0_hash = HASH (op0, mode);

	      /* If OP0 is contained in OP1, this changes its hash code
		 as well.  Faster to rehash than to check, except
		 for the simple case of a constant.  */
	      if (! CONSTANT_P (op1))
		op1_hash = HASH (op1,mode);
	    }

	  op0_elt = insert (op0, NULL, op0_hash, mode);
	  op0_elt->in_memory = op0_in_memory;
	}

      qty = REG_QTY (REGNO (op0));
      ent = &qty_table[qty];

      ent->comparison_code = code;
      if (GET_CODE (op1) == REG)
	{
	  /* Look it up again--in case op0 and op1 are the same.  */
	  op1_elt = lookup (op1, op1_hash, mode);

	  /* Put OP1 in the hash table so it gets a new quantity number.  */
	  if (op1_elt == 0)
	    {
	      if (insert_regs (op1, NULL, 0))
		{
		  rehash_using_reg (op1);
		  op1_hash = HASH (op1, mode);
		}

	      op1_elt = insert (op1, NULL, op1_hash, mode);
	      op1_elt->in_memory = op1_in_memory;
	    }

	  ent->comparison_const = NULL_RTX;
	  ent->comparison_qty = REG_QTY (REGNO (op1));
	}
      else
	{
	  ent->comparison_const = op1;
	  ent->comparison_qty = -1;
	}

      return;
    }

  /* If either side is still missing an equivalence, make it now,
     then merge the equivalences.  */

  if (op0_elt == 0)
    {
      if (insert_regs (op0, NULL, 0))
	{
	  rehash_using_reg (op0);
	  op0_hash = HASH (op0, mode);
	}

      op0_elt = insert (op0, NULL, op0_hash, mode);
      op0_elt->in_memory = op0_in_memory;
    }

  if (op1_elt == 0)
    {
      if (insert_regs (op1, NULL, 0))
	{
	  rehash_using_reg (op1);
	  op1_hash = HASH (op1, mode);
	}

      op1_elt = insert (op1, NULL, op1_hash, mode);
      op1_elt->in_memory = op1_in_memory;
    }

  merge_equiv_classes (op0_elt, op1_elt);
  last_jump_equiv_class = op0_elt;
}

/* CSE processing for one instruction.
   First simplify sources and addresses of all assignments
   in the instruction, using previously-computed equivalents values.
   Then install the new sources and destinations in the table
   of available values.

   If LIBCALL_INSN is nonzero, don't record any equivalence made in
   the insn.  It means that INSN is inside libcall block.  In this
   case LIBCALL_INSN is the corresponding insn with REG_LIBCALL.  */

/* Data on one SET contained in the instruction.  */

struct set
{
  /* The SET rtx itself.  */
  rtx rtl;
  /* The SET_SRC of the rtx (the original value, if it is changing).  */
  rtx src;
  /* The hash-table element for the SET_SRC of the SET.  */
  struct table_elt *src_elt;
  /* Hash value for the SET_SRC.  */
  unsigned src_hash;
  /* Hash value for the SET_DEST.  */
  unsigned dest_hash;
  /* The SET_DEST, with SUBREG, etc., stripped.  */
  rtx inner_dest;
  /* Nonzero if the SET_SRC is in memory.  */
  char src_in_memory;
  /* Nonzero if the SET_SRC contains something
     whose value cannot be predicted and understood.  */
  char src_volatile;
  /* Original machine mode, in case it becomes a CONST_INT.  */
  enum machine_mode mode;
  /* A constant equivalent for SET_SRC, if any.  */
  rtx src_const;
  /* Original SET_SRC value used for libcall notes.  */
  rtx orig_src;
  /* Hash value of constant equivalent for SET_SRC.  */
  unsigned src_const_hash;
  /* Table entry for constant equivalent for SET_SRC, if any.  */
  struct table_elt *src_const_elt;
};

static void
cse_insn (insn, libcall_insn)
     rtx insn;
     rtx libcall_insn;
{
  rtx x = PATTERN (insn);
  int i;
  rtx tem;
  int n_sets = 0;

#ifdef HAVE_cc0
  /* Records what this insn does to set CC0.  */
  rtx this_insn_cc0 = 0;
  enum machine_mode this_insn_cc0_mode = VOIDmode;
#endif

  rtx src_eqv = 0;
  struct table_elt *src_eqv_elt = 0;
  int src_eqv_volatile = 0;
  int src_eqv_in_memory = 0;
  unsigned src_eqv_hash = 0;

  struct set *sets = (struct set *) 0;

  this_insn = insn;

  /* Find all the SETs and CLOBBERs in this instruction.
     Record all the SETs in the array `set' and count them.
     Also determine whether there is a CLOBBER that invalidates
     all memory references, or all references at varying addresses.  */

  if (GET_CODE (insn) == CALL_INSN)
    {
      for (tem = CALL_INSN_FUNCTION_USAGE (insn); tem; tem = XEXP (tem, 1))
	{
	  if (GET_CODE (XEXP (tem, 0)) == CLOBBER)
	    invalidate (SET_DEST (XEXP (tem, 0)), VOIDmode);
	  XEXP (tem, 0) = canon_reg (XEXP (tem, 0), insn);
	}
    }

  if (GET_CODE (x) == SET)
    {
      sets = (struct set *) alloca (sizeof (struct set));
      sets[0].rtl = x;

      /* Ignore SETs that are unconditional jumps.
	 They never need cse processing, so this does not hurt.
	 The reason is not efficiency but rather
	 so that we can test at the end for instructions
	 that have been simplified to unconditional jumps
	 and not be misled by unchanged instructions
	 that were unconditional jumps to begin with.  */
      if (SET_DEST (x) == pc_rtx
	  && GET_CODE (SET_SRC (x)) == LABEL_REF)
	;

      /* Don't count call-insns, (set (reg 0) (call ...)), as a set.
	 The hard function value register is used only once, to copy to
	 someplace else, so it isn't worth cse'ing (and on 80386 is unsafe)!
	 Ensure we invalidate the destination register.  On the 80386 no
	 other code would invalidate it since it is a fixed_reg.
	 We need not check the return of apply_change_group; see canon_reg.  */

      else if (GET_CODE (SET_SRC (x)) == CALL)
	{
	  canon_reg (SET_SRC (x), insn);
	  apply_change_group ();
	  fold_rtx (SET_SRC (x), insn);
	  invalidate (SET_DEST (x), VOIDmode);
	}
      else
	n_sets = 1;
    }
  else if (GET_CODE (x) == PARALLEL)
    {
      int lim = XVECLEN (x, 0);

      sets = (struct set *) alloca (lim * sizeof (struct set));

      /* Find all regs explicitly clobbered in this insn,
	 and ensure they are not replaced with any other regs
	 elsewhere in this insn.
	 When a reg that is clobbered is also used for input,
	 we should presume that that is for a reason,
	 and we should not substitute some other register
	 which is not supposed to be clobbered.
	 Therefore, this loop cannot be merged into the one below
	 because a CALL may precede a CLOBBER and refer to the
	 value clobbered.  We must not let a canonicalization do
	 anything in that case.  */
      for (i = 0; i < lim; i++)
	{
	  rtx y = XVECEXP (x, 0, i);
	  if (GET_CODE (y) == CLOBBER)
	    {
	      rtx clobbered = XEXP (y, 0);

	      if (GET_CODE (clobbered) == REG
		  || GET_CODE (clobbered) == SUBREG)
		invalidate (clobbered, VOIDmode);
	      else if (GET_CODE (clobbered) == STRICT_LOW_PART
		       || GET_CODE (clobbered) == ZERO_EXTRACT)
		invalidate (XEXP (clobbered, 0), GET_MODE (clobbered));
	    }
	}

      for (i = 0; i < lim; i++)
	{
	  rtx y = XVECEXP (x, 0, i);
	  if (GET_CODE (y) == SET)
	    {
	      /* As above, we ignore unconditional jumps and call-insns and
		 ignore the result of apply_change_group.  */
	      if (GET_CODE (SET_SRC (y)) == CALL)
		{
		  canon_reg (SET_SRC (y), insn);
		  apply_change_group ();
		  fold_rtx (SET_SRC (y), insn);
		  invalidate (SET_DEST (y), VOIDmode);
		}
	      else if (SET_DEST (y) == pc_rtx
		       && GET_CODE (SET_SRC (y)) == LABEL_REF)
		;
	      else
		sets[n_sets++].rtl = y;
	    }
	  else if (GET_CODE (y) == CLOBBER)
	    {
	      /* If we clobber memory, canon the address.
		 This does nothing when a register is clobbered
		 because we have already invalidated the reg.  */
	      if (GET_CODE (XEXP (y, 0)) == MEM)
		canon_reg (XEXP (y, 0), NULL_RTX);
	    }
	  else if (GET_CODE (y) == USE
		   && ! (GET_CODE (XEXP (y, 0)) == REG
			 && REGNO (XEXP (y, 0)) < FIRST_PSEUDO_REGISTER))
	    canon_reg (y, NULL_RTX);
	  else if (GET_CODE (y) == CALL)
	    {
	      /* The result of apply_change_group can be ignored; see
		 canon_reg.  */
	      canon_reg (y, insn);
	      apply_change_group ();
	      fold_rtx (y, insn);
	    }
	}
    }
  else if (GET_CODE (x) == CLOBBER)
    {
      if (GET_CODE (XEXP (x, 0)) == MEM)
	canon_reg (XEXP (x, 0), NULL_RTX);
    }

  /* Canonicalize a USE of a pseudo register or memory location.  */
  else if (GET_CODE (x) == USE
	   && ! (GET_CODE (XEXP (x, 0)) == REG
		 && REGNO (XEXP (x, 0)) < FIRST_PSEUDO_REGISTER))
    canon_reg (XEXP (x, 0), NULL_RTX);
  else if (GET_CODE (x) == CALL)
    {
      /* The result of apply_change_group can be ignored; see canon_reg.  */
      canon_reg (x, insn);
      apply_change_group ();
      fold_rtx (x, insn);
    }

  /* Store the equivalent value in SRC_EQV, if different, or if the DEST
     is a STRICT_LOW_PART.  The latter condition is necessary because SRC_EQV
     is handled specially for this case, and if it isn't set, then there will
     be no equivalence for the destination.  */
  if (n_sets == 1 && REG_NOTES (insn) != 0
      && (tem = find_reg_note (insn, REG_EQUAL, NULL_RTX)) != 0
      && (! rtx_equal_p (XEXP (tem, 0), SET_SRC (sets[0].rtl))
	  || GET_CODE (SET_DEST (sets[0].rtl)) == STRICT_LOW_PART))
    {
      src_eqv = fold_rtx (canon_reg (XEXP (tem, 0), NULL_RTX), insn);
      XEXP (tem, 0) = src_eqv;
    }

  /* Canonicalize sources and addresses of destinations.
     We do this in a separate pass to avoid problems when a MATCH_DUP is
     present in the insn pattern.  In that case, we want to ensure that
     we don't break the duplicate nature of the pattern.  So we will replace
     both operands at the same time.  Otherwise, we would fail to find an
     equivalent substitution in the loop calling validate_change below.

     We used to suppress canonicalization of DEST if it appears in SRC,
     but we don't do this any more.  */

  for (i = 0; i < n_sets; i++)
    {
      rtx dest = SET_DEST (sets[i].rtl);
      rtx src = SET_SRC (sets[i].rtl);
      rtx new = canon_reg (src, insn);
      int insn_code;

      sets[i].orig_src = src;
      if ((GET_CODE (new) == REG && GET_CODE (src) == REG
	   && ((REGNO (new) < FIRST_PSEUDO_REGISTER)
	       != (REGNO (src) < FIRST_PSEUDO_REGISTER)))
	  || (insn_code = recog_memoized (insn)) < 0
	  || insn_data[insn_code].n_dups > 0)
	validate_change (insn, &SET_SRC (sets[i].rtl), new, 1);
      else
	SET_SRC (sets[i].rtl) = new;

      if (GET_CODE (dest) == ZERO_EXTRACT || GET_CODE (dest) == SIGN_EXTRACT)
	{
	  validate_change (insn, &XEXP (dest, 1),
			   canon_reg (XEXP (dest, 1), insn), 1);
	  validate_change (insn, &XEXP (dest, 2),
			   canon_reg (XEXP (dest, 2), insn), 1);
	}

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

      if (GET_CODE (dest) == MEM)
	canon_reg (dest, insn);
    }

  /* Now that we have done all the replacements, we can apply the change
     group and see if they all work.  Note that this will cause some
     canonicalizations that would have worked individually not to be applied
     because some other canonicalization didn't work, but this should not
     occur often.

     The result of apply_change_group can be ignored; see canon_reg.  */

  apply_change_group ();

  /* Set sets[i].src_elt to the class each source belongs to.
     Detect assignments from or to volatile things
     and set set[i] to zero so they will be ignored
     in the rest of this function.

     Nothing in this loop changes the hash table or the register chains.  */

  for (i = 0; i < n_sets; i++)
    {
      rtx src, dest;
      rtx src_folded;
      struct table_elt *elt = 0, *p;
      enum machine_mode mode;
      rtx src_eqv_here;
      rtx src_const = 0;
      rtx src_related = 0;
      struct table_elt *src_const_elt = 0;
      int src_cost = MAX_COST;
      int src_eqv_cost = MAX_COST;
      int src_folded_cost = MAX_COST;
      int src_related_cost = MAX_COST;
      int src_elt_cost = MAX_COST;
      int src_regcost = MAX_COST;
      int src_eqv_regcost = MAX_COST;
      int src_folded_regcost = MAX_COST;
      int src_related_regcost = MAX_COST;
      int src_elt_regcost = MAX_COST;
      /* Set nonzero if we need to call force_const_mem on with the
	 contents of src_folded before using it.  */
      int src_folded_force_flag = 0;

      dest = SET_DEST (sets[i].rtl);
      src = SET_SRC (sets[i].rtl);

      /* If SRC is a constant that has no machine mode,
	 hash it with the destination's machine mode.
	 This way we can keep different modes separate.  */

      mode = GET_MODE (src) == VOIDmode ? GET_MODE (dest) : GET_MODE (src);
      sets[i].mode = mode;

      if (src_eqv)
	{
	  enum machine_mode eqvmode = mode;
	  if (GET_CODE (dest) == STRICT_LOW_PART)
	    eqvmode = GET_MODE (SUBREG_REG (XEXP (dest, 0)));
	  do_not_record = 0;
	  hash_arg_in_memory = 0;
	  src_eqv_hash = HASH (src_eqv, eqvmode);

	  /* Find the equivalence class for the equivalent expression.  */

	  if (!do_not_record)
	    src_eqv_elt = lookup (src_eqv, src_eqv_hash, eqvmode);

	  src_eqv_volatile = do_not_record;
	  src_eqv_in_memory = hash_arg_in_memory;
	}

      /* If this is a STRICT_LOW_PART assignment, src_eqv corresponds to the
	 value of the INNER register, not the destination.  So it is not
	 a valid substitution for the source.  But save it for later.  */
      if (GET_CODE (dest) == STRICT_LOW_PART)
	src_eqv_here = 0;
      else
	src_eqv_here = src_eqv;

      /* Simplify and foldable subexpressions in SRC.  Then get the fully-
	 simplified result, which may not necessarily be valid.  */
      src_folded = fold_rtx (src, insn);

#if 0
      /* ??? This caused bad code to be generated for the m68k port with -O2.
	 Suppose src is (CONST_INT -1), and that after truncation src_folded
	 is (CONST_INT 3).  Suppose src_folded is then used for src_const.
	 At the end we will add src and src_const to the same equivalence
	 class.  We now have 3 and -1 on the same equivalence class.  This
	 causes later instructions to be mis-optimized.  */
      /* If storing a constant in a bitfield, pre-truncate the constant
	 so we will be able to record it later.  */
      if (GET_CODE (SET_DEST (sets[i].rtl)) == ZERO_EXTRACT
	  || GET_CODE (SET_DEST (sets[i].rtl)) == SIGN_EXTRACT)
	{
	  rtx width = XEXP (SET_DEST (sets[i].rtl), 1);

	  if (GET_CODE (src) == CONST_INT
	      && GET_CODE (width) == CONST_INT
	      && INTVAL (width) < HOST_BITS_PER_WIDE_INT
	      && (INTVAL (src) & ((HOST_WIDE_INT) (-1) << INTVAL (width))))
	    src_folded
	      = GEN_INT (INTVAL (src) & (((HOST_WIDE_INT) 1
					  << INTVAL (width)) - 1));
	}
#endif

      /* Compute SRC's hash code, and also notice if it
	 should not be recorded at all.  In that case,
	 prevent any further processing of this assignment.  */
      do_not_record = 0;
      hash_arg_in_memory = 0;

      sets[i].src = src;
      sets[i].src_hash = HASH (src, mode);
      sets[i].src_volatile = do_not_record;
      sets[i].src_in_memory = hash_arg_in_memory;

      /* If SRC is a MEM, there is a REG_EQUIV note for SRC, and DEST is
	 a pseudo, do not record SRC.  Using SRC as a replacement for
	 anything else will be incorrect in that situation.  Note that
	 this usually occurs only for stack slots, in which case all the
	 RTL would be referring to SRC, so we don't lose any optimization
	 opportunities by not having SRC in the hash table.  */

      if (GET_CODE (src) == MEM
	  && find_reg_note (insn, REG_EQUIV, NULL_RTX) != 0
	  && GET_CODE (dest) == REG
	  && REGNO (dest) >= FIRST_PSEUDO_REGISTER)
	sets[i].src_volatile = 1;

#if 0
      /* It is no longer clear why we used to do this, but it doesn't
	 appear to still be needed.  So let's try without it since this
	 code hurts cse'ing widened ops.  */
      /* If source is a perverse subreg (such as QI treated as an SI),
	 treat it as volatile.  It may do the work of an SI in one context
	 where the extra bits are not being used, but cannot replace an SI
	 in general.  */
      if (GET_CODE (src) == SUBREG
	  && (GET_MODE_SIZE (GET_MODE (src))
	      > GET_MODE_SIZE (GET_MODE (SUBREG_REG (src)))))
	sets[i].src_volatile = 1;
#endif

      /* Locate all possible equivalent forms for SRC.  Try to replace
         SRC in the insn with each cheaper equivalent.

         We have the following types of equivalents: SRC itself, a folded
         version, a value given in a REG_EQUAL note, or a value related
	 to a constant.

         Each of these equivalents may be part of an additional class
         of equivalents (if more than one is in the table, they must be in
         the same class; we check for this).

	 If the source is volatile, we don't do any table lookups.

         We note any constant equivalent for possible later use in a
         REG_NOTE.  */

      if (!sets[i].src_volatile)
	elt = lookup (src, sets[i].src_hash, mode);

      sets[i].src_elt = elt;

      if (elt && src_eqv_here && src_eqv_elt)
	{
	  if (elt->first_same_value != src_eqv_elt->first_same_value)
	    {
	      /* The REG_EQUAL is indicating that two formerly distinct
		 classes are now equivalent.  So merge them.  */
	      merge_equiv_classes (elt, src_eqv_elt);
	      src_eqv_hash = HASH (src_eqv, elt->mode);
	      src_eqv_elt = lookup (src_eqv, src_eqv_hash, elt->mode);
	    }

	  src_eqv_here = 0;
	}

      else if (src_eqv_elt)
	elt = src_eqv_elt;

      /* Try to find a constant somewhere and record it in `src_const'.
	 Record its table element, if any, in `src_const_elt'.  Look in
	 any known equivalences first.  (If the constant is not in the
	 table, also set `sets[i].src_const_hash').  */
      if (elt)
	for (p = elt->first_same_value; p; p = p->next_same_value)
	  if (p->is_const)
	    {
	      src_const = p->exp;
	      src_const_elt = elt;
	      break;
	    }

      if (src_const == 0
	  && (CONSTANT_P (src_folded)
	      /* Consider (minus (label_ref L1) (label_ref L2)) as
		 "constant" here so we will record it. This allows us
		 to fold switch statements when an ADDR_DIFF_VEC is used.  */
	      || (GET_CODE (src_folded) == MINUS
		  && GET_CODE (XEXP (src_folded, 0)) == LABEL_REF
		  && GET_CODE (XEXP (src_folded, 1)) == LABEL_REF)))
	src_const = src_folded, src_const_elt = elt;
      else if (src_const == 0 && src_eqv_here && CONSTANT_P (src_eqv_here))
	src_const = src_eqv_here, src_const_elt = src_eqv_elt;

      /* If we don't know if the constant is in the table, get its
	 hash code and look it up.  */
      if (src_const && src_const_elt == 0)
	{
	  sets[i].src_const_hash = HASH (src_const, mode);
	  src_const_elt = lookup (src_const, sets[i].src_const_hash, mode);
	}

      sets[i].src_const = src_const;
      sets[i].src_const_elt = src_const_elt;

      /* If the constant and our source are both in the table, mark them as
	 equivalent.  Otherwise, if a constant is in the table but the source
	 isn't, set ELT to it.  */
      if (src_const_elt && elt
	  && src_const_elt->first_same_value != elt->first_same_value)
	merge_equiv_classes (elt, src_const_elt);
      else if (src_const_elt && elt == 0)
	elt = src_const_elt;

      /* See if there is a register linearly related to a constant
         equivalent of SRC.  */
      if (src_const
	  && (GET_CODE (src_const) == CONST
	      || (src_const_elt && src_const_elt->related_value != 0)))
	{
	  src_related = use_related_value (src_const, src_const_elt);
	  if (src_related)
	    {
	      struct table_elt *src_related_elt
		= lookup (src_related, HASH (src_related, mode), mode);
	      if (src_related_elt && elt)
		{
		  if (elt->first_same_value
		      != src_related_elt->first_same_value)
		    /* This can occur when we previously saw a CONST
		       involving a SYMBOL_REF and then see the SYMBOL_REF
		       twice.  Merge the involved classes.  */
		    merge_equiv_classes (elt, src_related_elt);

		  src_related = 0;
		  src_related_elt = 0;
		}
	      else if (src_related_elt && elt == 0)
		elt = src_related_elt;
	    }
	}

      /* See if we have a CONST_INT that is already in a register in a
	 wider mode.  */

      if (src_const && src_related == 0 && GET_CODE (src_const) == CONST_INT
	  && GET_MODE_CLASS (mode) == MODE_INT
	  && GET_MODE_BITSIZE (mode) < BITS_PER_WORD)
	{
	  enum machine_mode wider_mode;

	  for (wider_mode = GET_MODE_WIDER_MODE (mode);
	       GET_MODE_BITSIZE (wider_mode) <= BITS_PER_WORD
	       && src_related == 0;
	       wider_mode = GET_MODE_WIDER_MODE (wider_mode))
	    {
	      struct table_elt *const_elt
		= lookup (src_const, HASH (src_const, wider_mode), wider_mode);

	      if (const_elt == 0)
		continue;

	      for (const_elt = const_elt->first_same_value;
		   const_elt; const_elt = const_elt->next_same_value)
		if (GET_CODE (const_elt->exp) == REG)
		  {
		    src_related = gen_lowpart_if_possible (mode,
							   const_elt->exp);
		    break;
		  }
	    }
	}

      /* Another possibility is that we have an AND with a constant in
	 a mode narrower than a word.  If so, it might have been generated
	 as part of an "if" which would narrow the AND.  If we already
	 have done the AND in a wider mode, we can use a SUBREG of that
	 value.  */

      if (flag_expensive_optimizations && ! src_related
	  && GET_CODE (src) == AND && GET_CODE (XEXP (src, 1)) == CONST_INT
	  && GET_MODE_SIZE (mode) < UNITS_PER_WORD)
	{
	  enum machine_mode tmode;
	  rtx new_and = gen_rtx_AND (VOIDmode, NULL_RTX, XEXP (src, 1));

	  for (tmode = GET_MODE_WIDER_MODE (mode);
	       GET_MODE_SIZE (tmode) <= UNITS_PER_WORD;
	       tmode = GET_MODE_WIDER_MODE (tmode))
	    {
	      rtx inner = gen_lowpart_if_possible (tmode, XEXP (src, 0));
	      struct table_elt *larger_elt;

	      if (inner)
		{
		  PUT_MODE (new_and, tmode);
		  XEXP (new_and, 0) = inner;
		  larger_elt = lookup (new_and, HASH (new_and, tmode), tmode);
		  if (larger_elt == 0)
		    continue;

		  for (larger_elt = larger_elt->first_same_value;
		       larger_elt; larger_elt = larger_elt->next_same_value)
		    if (GET_CODE (larger_elt->exp) == REG)
		      {
			src_related
			  = gen_lowpart_if_possible (mode, larger_elt->exp);
			break;
		      }

		  if (src_related)
		    break;
		}
	    }
	}

#ifdef LOAD_EXTEND_OP
      /* See if a MEM has already been loaded with a widening operation;
	 if it has, we can use a subreg of that.  Many CISC machines
	 also have such operations, but this is only likely to be
	 beneficial these machines.  */

      if (flag_expensive_optimizations && src_related == 0
	  && (GET_MODE_SIZE (mode) < UNITS_PER_WORD)
	  && GET_MODE_CLASS (mode) == MODE_INT
	  && GET_CODE (src) == MEM && ! do_not_record
	  && LOAD_EXTEND_OP (mode) != NIL)
	{
	  enum machine_mode tmode;

	  /* Set what we are trying to extend and the operation it might
	     have been extended with.  */
	  PUT_CODE (memory_extend_rtx, LOAD_EXTEND_OP (mode));
	  XEXP (memory_extend_rtx, 0) = src;

	  for (tmode = GET_MODE_WIDER_MODE (mode);
	       GET_MODE_SIZE (tmode) <= UNITS_PER_WORD;
	       tmode = GET_MODE_WIDER_MODE (tmode))
	    {
	      struct table_elt *larger_elt;

	      PUT_MODE (memory_extend_rtx, tmode);
	      larger_elt = lookup (memory_extend_rtx,
				   HASH (memory_extend_rtx, tmode), tmode);
	      if (larger_elt == 0)
		continue;

	      for (larger_elt = larger_elt->first_same_value;
		   larger_elt; larger_elt = larger_elt->next_same_value)
		if (GET_CODE (larger_elt->exp) == REG)
		  {
		    src_related = gen_lowpart_if_possible (mode,
							   larger_elt->exp);
		    break;
		  }

	      if (src_related)
		break;
	    }
	}
#endif /* LOAD_EXTEND_OP */

      if (src == src_folded)
	src_folded = 0;

      /* At this point, ELT, if nonzero, points to a class of expressions
         equivalent to the source of this SET and SRC, SRC_EQV, SRC_FOLDED,
	 and SRC_RELATED, if nonzero, each contain additional equivalent
	 expressions.  Prune these latter expressions by deleting expressions
	 already in the equivalence class.

	 Check for an equivalent identical to the destination.  If found,
	 this is the preferred equivalent since it will likely lead to
	 elimination of the insn.  Indicate this by placing it in
	 `src_related'.  */

      if (elt)
	elt = elt->first_same_value;
      for (p = elt; p; p = p->next_same_value)
	{
	  enum rtx_code code = GET_CODE (p->exp);

	  /* If the expression is not valid, ignore it.  Then we do not
	     have to check for validity below.  In most cases, we can use
	     `rtx_equal_p', since canonicalization has already been done.  */
	  if (code != REG && ! exp_equiv_p (p->exp, p->exp, 1, 0))
	    continue;

	  /* Also skip paradoxical subregs, unless that's what we're
	     looking for.  */
	  if (code == SUBREG
	      && (GET_MODE_SIZE (GET_MODE (p->exp))
		  > GET_MODE_SIZE (GET_MODE (SUBREG_REG (p->exp))))
	      && ! (src != 0
		    && GET_CODE (src) == SUBREG
		    && GET_MODE (src) == GET_MODE (p->exp)
		    && (GET_MODE_SIZE (GET_MODE (SUBREG_REG (src)))
			< GET_MODE_SIZE (GET_MODE (SUBREG_REG (p->exp))))))
	    continue;

	  if (src && GET_CODE (src) == code && rtx_equal_p (src, p->exp))
	    src = 0;
	  else if (src_folded && GET_CODE (src_folded) == code
		   && rtx_equal_p (src_folded, p->exp))
	    src_folded = 0;
	  else if (src_eqv_here && GET_CODE (src_eqv_here) == code
		   && rtx_equal_p (src_eqv_here, p->exp))
	    src_eqv_here = 0;
	  else if (src_related && GET_CODE (src_related) == code
		   && rtx_equal_p (src_related, p->exp))
	    src_related = 0;

	  /* This is the same as the destination of the insns, we want
	     to prefer it.  Copy it to src_related.  The code below will
	     then give it a negative cost.  */
	  if (GET_CODE (dest) == code && rtx_equal_p (p->exp, dest))
	    src_related = dest;
	}

      /* Find the cheapest valid equivalent, trying all the available
         possibilities.  Prefer items not in the hash table to ones
         that are when they are equal cost.  Note that we can never
         worsen an insn as the current contents will also succeed.
	 If we find an equivalent identical to the destination, use it as best,
	 since this insn will probably be eliminated in that case.  */
      if (src)
	{
	  if (rtx_equal_p (src, dest))
	    src_cost = src_regcost = -1;
	  else
	    {
	      src_cost = COST (src);
	      src_regcost = approx_reg_cost (src);
	    }
	}

      if (src_eqv_here)
	{
	  if (rtx_equal_p (src_eqv_here, dest))
	    src_eqv_cost = src_eqv_regcost = -1;
	  else
	    {
	      src_eqv_cost = COST (src_eqv_here);
	      src_eqv_regcost = approx_reg_cost (src_eqv_here);
	    }
	}

      if (src_folded)
	{
	  if (rtx_equal_p (src_folded, dest))
	    src_folded_cost = src_folded_regcost = -1;
	  else
	    {
	      src_folded_cost = COST (src_folded);
	      src_folded_regcost = approx_reg_cost (src_folded);
	    }
	}

      if (src_related)
	{
	  if (rtx_equal_p (src_related, dest))
	    src_related_cost = src_related_regcost = -1;
	  else
	    {
	      src_related_cost = COST (src_related);
	      src_related_regcost = approx_reg_cost (src_related);
	    }
	}

      /* If this was an indirect jump insn, a known label will really be
	 cheaper even though it looks more expensive.  */
      if (dest == pc_rtx && src_const && GET_CODE (src_const) == LABEL_REF)
	src_folded = src_const, src_folded_cost = src_folded_regcost = -1;

      /* Terminate loop when replacement made.  This must terminate since
         the current contents will be tested and will always be valid.  */
      while (1)
	{
	  rtx trial;

	  /* Skip invalid entries.  */
	  while (elt && GET_CODE (elt->exp) != REG
		 && ! exp_equiv_p (elt->exp, elt->exp, 1, 0))
	    elt = elt->next_same_value;

	  /* A paradoxical subreg would be bad here: it'll be the right
	     size, but later may be adjusted so that the upper bits aren't
	     what we want.  So reject it.  */
	  if (elt != 0
	      && GET_CODE (elt->exp) == SUBREG
	      && (GET_MODE_SIZE (GET_MODE (elt->exp))
		  > GET_MODE_SIZE (GET_MODE (SUBREG_REG (elt->exp))))
	      /* It is okay, though, if the rtx we're trying to match
		 will ignore any of the bits we can't predict.  */
	      && ! (src != 0
		    && GET_CODE (src) == SUBREG
		    && GET_MODE (src) == GET_MODE (elt->exp)
		    && (GET_MODE_SIZE (GET_MODE (SUBREG_REG (src)))
			< GET_MODE_SIZE (GET_MODE (SUBREG_REG (elt->exp))))))
	    {
	      elt = elt->next_same_value;
	      continue;
	    }

	  if (elt)
	    {
	      src_elt_cost = elt->cost;
	      src_elt_regcost = elt->regcost;
	    }

	  /* Find cheapest and skip it for the next time.   For items
	     of equal cost, use this order:
	     src_folded, src, src_eqv, src_related and hash table entry.  */
	  if (src_folded
	      && preferrable (src_folded_cost, src_folded_regcost,
			      src_cost, src_regcost) <= 0
	      && preferrable (src_folded_cost, src_folded_regcost,
			      src_eqv_cost, src_eqv_regcost) <= 0
	      && preferrable (src_folded_cost, src_folded_regcost,
			      src_related_cost, src_related_regcost) <= 0
	      && preferrable (src_folded_cost, src_folded_regcost,
			      src_elt_cost, src_elt_regcost) <= 0)
	    {
	      trial = src_folded, src_folded_cost = MAX_COST;
	      if (src_folded_force_flag)
		trial = force_const_mem (mode, trial);
	    }
	  else if (src
		   && preferrable (src_cost, src_regcost,
				   src_eqv_cost, src_eqv_regcost) <= 0
		   && preferrable (src_cost, src_regcost,
				   src_related_cost, src_related_regcost) <= 0
		   && preferrable (src_cost, src_regcost,
				   src_elt_cost, src_elt_regcost) <= 0)
	    trial = src, src_cost = MAX_COST;
	  else if (src_eqv_here
		   && preferrable (src_eqv_cost, src_eqv_regcost,
				   src_related_cost, src_related_regcost) <= 0
		   && preferrable (src_eqv_cost, src_eqv_regcost,
				   src_elt_cost, src_elt_regcost) <= 0)
	    trial = copy_rtx (src_eqv_here), src_eqv_cost = MAX_COST;
	  else if (src_related
		   && preferrable (src_related_cost, src_related_regcost,
				   src_elt_cost, src_elt_regcost) <= 0)
	    trial = copy_rtx (src_related), src_related_cost = MAX_COST;
	  else
	    {
	      trial = copy_rtx (elt->exp);
	      elt = elt->next_same_value;
	      src_elt_cost = MAX_COST;
	    }

	  /* We don't normally have an insn matching (set (pc) (pc)), so
	     check for this separately here.  We will delete such an
	     insn below.

	     For other cases such as a table jump or conditional jump
	     where we know the ultimate target, go ahead and replace the
	     operand.  While that may not make a valid insn, we will
	     reemit the jump below (and also insert any necessary
	     barriers).  */
	  if (n_sets == 1 && dest == pc_rtx
	      && (trial == pc_rtx
		  || (GET_CODE (trial) == LABEL_REF
		      && ! condjump_p (insn))))
	    {
	      SET_SRC (sets[i].rtl) = trial;
	      cse_jumps_altered = 1;
	      break;
	    }

	  /* Look for a substitution that makes a valid insn.  */
	  else if (validate_change (insn, &SET_SRC (sets[i].rtl), trial, 0))
	    {
	      /* If we just made a substitution inside a libcall, then we
		 need to make the same substitution in any notes attached
		 to the RETVAL insn.  */
	      if (libcall_insn
		  && (GET_CODE (sets[i].orig_src) == REG
		      || GET_CODE (sets[i].orig_src) == SUBREG
		      || GET_CODE (sets[i].orig_src) == MEM))
		replace_rtx (REG_NOTES (libcall_insn), sets[i].orig_src,
			     canon_reg (SET_SRC (sets[i].rtl), insn));

	      /* The result of apply_change_group can be ignored; see
		 canon_reg.  */

	      validate_change (insn, &SET_SRC (sets[i].rtl),
			       canon_reg (SET_SRC (sets[i].rtl), insn),
			       1);
	      apply_change_group ();
	      break;
	    }

	  /* If we previously found constant pool entries for
	     constants and this is a constant, try making a
	     pool entry.  Put it in src_folded unless we already have done
	     this since that is where it likely came from.  */

	  else if (constant_pool_entries_cost
		   && CONSTANT_P (trial)
		   /* Reject cases that will abort in decode_rtx_const.
		      On the alpha when simplifying a switch, we get
		      (const (truncate (minus (label_ref) (label_ref)))).  */
		   && ! (GET_CODE (trial) == CONST
			 && GET_CODE (XEXP (trial, 0)) == TRUNCATE)
		   /* Likewise on IA-64, except without the truncate.  */
		   && ! (GET_CODE (trial) == CONST
			 && GET_CODE (XEXP (trial, 0)) == MINUS
			 && GET_CODE (XEXP (XEXP (trial, 0), 0)) == LABEL_REF
			 && GET_CODE (XEXP (XEXP (trial, 0), 1)) == LABEL_REF)
		   && (src_folded == 0
		       || (GET_CODE (src_folded) != MEM
			   && ! src_folded_force_flag))
		   && GET_MODE_CLASS (mode) != MODE_CC
		   && mode != VOIDmode)
	    {
	      src_folded_force_flag = 1;
	      src_folded = trial;
	      src_folded_cost = constant_pool_entries_cost;
	    }
	}

      src = SET_SRC (sets[i].rtl);

      /* In general, it is good to have a SET with SET_SRC == SET_DEST.
	 However, there is an important exception:  If both are registers
	 that are not the head of their equivalence class, replace SET_SRC
	 with the head of the class.  If we do not do this, we will have
	 both registers live over a portion of the basic block.  This way,
	 their lifetimes will likely abut instead of overlapping.  */
      if (GET_CODE (dest) == REG
	  && REGNO_QTY_VALID_P (REGNO (dest)))
	{
	  int dest_q = REG_QTY (REGNO (dest));
	  struct qty_table_elem *dest_ent = &qty_table[dest_q];

	  if (dest_ent->mode == GET_MODE (dest)
	      && dest_ent->first_reg != REGNO (dest)
	      && GET_CODE (src) == REG && REGNO (src) == REGNO (dest)
	      /* Don't do this if the original insn had a hard reg as
		 SET_SRC or SET_DEST.  */
	      && (GET_CODE (sets[i].src) != REG
		  || REGNO (sets[i].src) >= FIRST_PSEUDO_REGISTER)
	      && (GET_CODE (dest) != REG || REGNO (dest) >= FIRST_PSEUDO_REGISTER))
	    /* We can't call canon_reg here because it won't do anything if
	       SRC is a hard register.  */
	    {
	      int src_q = REG_QTY (REGNO (src));
	      struct qty_table_elem *src_ent = &qty_table[src_q];
	      int first = src_ent->first_reg;
	      rtx new_src
		= (first >= FIRST_PSEUDO_REGISTER
		   ? regno_reg_rtx[first] : gen_rtx_REG (GET_MODE (src), first));

	      /* We must use validate-change even for this, because this
		 might be a special no-op instruction, suitable only to
		 tag notes onto.  */
	      if (validate_change (insn, &SET_SRC (sets[i].rtl), new_src, 0))
		{
		  src = new_src;
		  /* If we had a constant that is cheaper than what we are now
		     setting SRC to, use that constant.  We ignored it when we
		     thought we could make this into a no-op.  */
		  if (src_const && COST (src_const) < COST (src)
		      && validate_change (insn, &SET_SRC (sets[i].rtl),
					  src_const, 0))
		    src = src_const;
		}
	    }
	}

      /* If we made a change, recompute SRC values.  */
      if (src != sets[i].src)
	{
	  cse_altered = 1;
	  do_not_record = 0;
	  hash_arg_in_memory = 0;
	  sets[i].src = src;
	  sets[i].src_hash = HASH (src, mode);
	  sets[i].src_volatile = do_not_record;
	  sets[i].src_in_memory = hash_arg_in_memory;
	  sets[i].src_elt = lookup (src, sets[i].src_hash, mode);
	}

      /* If this is a single SET, we are setting a register, and we have an
	 equivalent constant, we want to add a REG_NOTE.   We don't want
	 to write a REG_EQUAL note for a constant pseudo since verifying that
	 that pseudo hasn't been eliminated is a pain.  Such a note also
	 won't help anything.

	 Avoid a REG_EQUAL note for (CONST (MINUS (LABEL_REF) (LABEL_REF)))
	 which can be created for a reference to a compile time computable
	 entry in a jump table.  */

      if (n_sets == 1 && src_const && GET_CODE (dest) == REG
	  && GET_CODE (src_const) != REG
	  && ! (GET_CODE (src_const) == CONST
		&& GET_CODE (XEXP (src_const, 0)) == MINUS
		&& GET_CODE (XEXP (XEXP (src_const, 0), 0)) == LABEL_REF
		&& GET_CODE (XEXP (XEXP (src_const, 0), 1)) == LABEL_REF))
	{
	  /* Make sure that the rtx is not shared with any other insn.  */
	  src_const = copy_rtx (src_const);

	  /* Record the actual constant value in a REG_EQUAL note, making
	     a new one if one does not already exist.  */
	  set_unique_reg_note (insn, REG_EQUAL, src_const);

	  /* If storing a constant value in a register that
	     previously held the constant value 0,
	     record this fact with a REG_WAS_0 note on this insn.

	     Note that the *register* is required to have previously held 0,
	     not just any register in the quantity and we must point to the
	     insn that set that register to zero.

	     Rather than track each register individually, we just see if
	     the last set for this quantity was for this register.  */

	  if (REGNO_QTY_VALID_P (REGNO (dest)))
	    {
	      int dest_q = REG_QTY (REGNO (dest));
	      struct qty_table_elem *dest_ent = &qty_table[dest_q];

	      if (dest_ent->const_rtx == const0_rtx)
		{
		  /* See if we previously had a REG_WAS_0 note.  */
		  rtx note = find_reg_note (insn, REG_WAS_0, NULL_RTX);
		  rtx const_insn = dest_ent->const_insn;

		  if ((tem = single_set (const_insn)) != 0
		      && rtx_equal_p (SET_DEST (tem), dest))
		    {
		      if (note)
			XEXP (note, 0) = const_insn;
		      else
			REG_NOTES (insn)
			  = gen_rtx_INSN_LIST (REG_WAS_0, const_insn,
					       REG_NOTES (insn));
		    }
		}
	    }
	}

      /* Now deal with the destination.  */
      do_not_record = 0;

      /* Look within any SIGN_EXTRACT or ZERO_EXTRACT
	 to the MEM or REG within it.  */
      while (GET_CODE (dest) == SIGN_EXTRACT
	     || GET_CODE (dest) == ZERO_EXTRACT
	     || GET_CODE (dest) == SUBREG
	     || GET_CODE (dest) == STRICT_LOW_PART)
	dest = XEXP (dest, 0);

      sets[i].inner_dest = dest;

      if (GET_CODE (dest) == MEM)
	{
#ifdef PUSH_ROUNDING
	  /* Stack pushes invalidate the stack pointer.  */
	  rtx addr = XEXP (dest, 0);
	  if (GET_RTX_CLASS (GET_CODE (addr)) == 'a'
	      && XEXP (addr, 0) == stack_pointer_rtx)
	    invalidate (stack_pointer_rtx, Pmode);
#endif
	  dest = fold_rtx (dest, insn);
	}

      /* Compute the hash code of the destination now,
	 before the effects of this instruction are recorded,
	 since the register values used in the address computation
	 are those before this instruction.  */
      sets[i].dest_hash = HASH (dest, mode);

      /* Don't enter a bit-field in the hash table
	 because the value in it after the store
	 may not equal what was stored, due to truncation.  */

      if (GET_CODE (SET_DEST (sets[i].rtl)) == ZERO_EXTRACT
	  || GET_CODE (SET_DEST (sets[i].rtl)) == SIGN_EXTRACT)
	{
	  rtx width = XEXP (SET_DEST (sets[i].rtl), 1);

	  if (src_const != 0 && GET_CODE (src_const) == CONST_INT
	      && GET_CODE (width) == CONST_INT
	      && INTVAL (width) < HOST_BITS_PER_WIDE_INT
	      && ! (INTVAL (src_const)
		    & ((HOST_WIDE_INT) (-1) << INTVAL (width))))
	    /* Exception: if the value is constant,
	       and it won't be truncated, record it.  */
	    ;
	  else
	    {
	      /* This is chosen so that the destination will be invalidated
		 but no new value will be recorded.
		 We must invalidate because sometimes constant
		 values can be recorded for bitfields.  */
	      sets[i].src_elt = 0;
	      sets[i].src_volatile = 1;
	      src_eqv = 0;
	      src_eqv_elt = 0;
	    }
	}

      /* If only one set in a JUMP_INSN and it is now a no-op, we can delete
	 the insn.  */
      else if (n_sets == 1 && dest == pc_rtx && src == pc_rtx)
	{
	  /* One less use of the label this insn used to jump to.  */
	  delete_insn (insn);
	  cse_jumps_altered = 1;
	  /* No more processing for this set.  */
	  sets[i].rtl = 0;
	}

      /* If this SET is now setting PC to a label, we know it used to
	 be a conditional or computed branch.  */
      else if (dest == pc_rtx && GET_CODE (src) == LABEL_REF)
	{
	  /* Now emit a BARRIER after the unconditional jump.  */
	  if (NEXT_INSN (insn) == 0
	      || GET_CODE (NEXT_INSN (insn)) != BARRIER)
	    emit_barrier_after (insn);

	  /* We reemit the jump in as many cases as possible just in
	     case the form of an unconditional jump is significantly
	     different than a computed jump or conditional jump.

	     If this insn has multiple sets, then reemitting the
	     jump is nontrivial.  So instead we just force rerecognition
	     and hope for the best.  */
	  if (n_sets == 1)
	    {
	      rtx new = emit_jump_insn_after (gen_jump (XEXP (src, 0)), insn);

	      JUMP_LABEL (new) = XEXP (src, 0);
	      LABEL_NUSES (XEXP (src, 0))++;
	      delete_insn (insn);
	      insn = new;

	      /* Now emit a BARRIER after the unconditional jump.  */
	      if (NEXT_INSN (insn) == 0
		  || GET_CODE (NEXT_INSN (insn)) != BARRIER)
		emit_barrier_after (insn);
	    }
	  else
	    INSN_CODE (insn) = -1;

	  never_reached_warning (insn, NULL);

	  /* Do not bother deleting any unreachable code,
	     let jump/flow do that.  */

	  cse_jumps_altered = 1;
	  sets[i].rtl = 0;
	}

      /* If destination is volatile, invalidate it and then do no further
	 processing for this assignment.  */

      else if (do_not_record)
	{
	  if (GET_CODE (dest) == REG || GET_CODE (dest) == SUBREG)
	    invalidate (dest, VOIDmode);
	  else if (GET_CODE (dest) == MEM)
	    {
	      /* Outgoing arguments for a libcall don't
		 affect any recorded expressions.  */
	      if (! libcall_insn || insn == libcall_insn)
		invalidate (dest, VOIDmode);
	    }
	  else if (GET_CODE (dest) == STRICT_LOW_PART
		   || GET_CODE (dest) == ZERO_EXTRACT)
	    invalidate (XEXP (dest, 0), GET_MODE (dest));
	  sets[i].rtl = 0;
	}

      if (sets[i].rtl != 0 && dest != SET_DEST (sets[i].rtl))
	sets[i].dest_hash = HASH (SET_DEST (sets[i].rtl), mode);

#ifdef HAVE_cc0
      /* If setting CC0, record what it was set to, or a constant, if it
	 is equivalent to a constant.  If it is being set to a floating-point
	 value, make a COMPARE with the appropriate constant of 0.  If we
	 don't do this, later code can interpret this as a test against
	 const0_rtx, which can cause problems if we try to put it into an
	 insn as a floating-point operand.  */
      if (dest == cc0_rtx)
	{
	  this_insn_cc0 = src_const && mode != VOIDmode ? src_const : src;
	  this_insn_cc0_mode = mode;
	  if (FLOAT_MODE_P (mode))
	    this_insn_cc0 = gen_rtx_COMPARE (VOIDmode, this_insn_cc0,
					     CONST0_RTX (mode));
	}
#endif
    }

  /* Now enter all non-volatile source expressions in the hash table
     if they are not already present.
     Record their equivalence classes in src_elt.
     This way we can insert the corresponding destinations into
     the same classes even if the actual sources are no longer in them
     (having been invalidated).  */

  if (src_eqv && src_eqv_elt == 0 && sets[0].rtl != 0 && ! src_eqv_volatile
      && ! rtx_equal_p (src_eqv, SET_DEST (sets[0].rtl)))
    {
      struct table_elt *elt;
      struct table_elt *classp = sets[0].src_elt;
      rtx dest = SET_DEST (sets[0].rtl);
      enum machine_mode eqvmode = GET_MODE (dest);

      if (GET_CODE (dest) == STRICT_LOW_PART)
	{
	  eqvmode = GET_MODE (SUBREG_REG (XEXP (dest, 0)));
	  classp = 0;
	}
      if (insert_regs (src_eqv, classp, 0))
	{
	  rehash_using_reg (src_eqv);
	  src_eqv_hash = HASH (src_eqv, eqvmode);
	}
      elt = insert (src_eqv, classp, src_eqv_hash, eqvmode);
      elt->in_memory = src_eqv_in_memory;
      src_eqv_elt = elt;

      /* Check to see if src_eqv_elt is the same as a set source which
	 does not yet have an elt, and if so set the elt of the set source
	 to src_eqv_elt.  */
      for (i = 0; i < n_sets; i++)
	if (sets[i].rtl && sets[i].src_elt == 0
	    && rtx_equal_p (SET_SRC (sets[i].rtl), src_eqv))
	  sets[i].src_elt = src_eqv_elt;
    }

  for (i = 0; i < n_sets; i++)
    if (sets[i].rtl && ! sets[i].src_volatile
	&& ! rtx_equal_p (SET_SRC (sets[i].rtl), SET_DEST (sets[i].rtl)))
      {
	if (GET_CODE (SET_DEST (sets[i].rtl)) == STRICT_LOW_PART)
	  {
	    /* REG_EQUAL in setting a STRICT_LOW_PART
	       gives an equivalent for the entire destination register,
	       not just for the subreg being stored in now.
	       This is a more interesting equivalence, so we arrange later
	       to treat the entire reg as the destination.  */
	    sets[i].src_elt = src_eqv_elt;
	    sets[i].src_hash = src_eqv_hash;
	  }
	else
	  {
	    /* Insert source and constant equivalent into hash table, if not
	       already present.  */
	    struct table_elt *classp = src_eqv_elt;
	    rtx src = sets[i].src;
	    rtx dest = SET_DEST (sets[i].rtl);
	    enum machine_mode mode
	      = GET_MODE (src) == VOIDmode ? GET_MODE (dest) : GET_MODE (src);

	    if (sets[i].src_elt == 0)
	      {
		/* Don't put a hard register source into the table if this is
		   the last insn of a libcall.  In this case, we only need
		   to put src_eqv_elt in src_elt.  */
		if (! find_reg_note (insn, REG_RETVAL, NULL_RTX))
		  {
		    struct table_elt *elt;

		    /* Note that these insert_regs calls cannot remove
		       any of the src_elt's, because they would have failed to
		       match if not still valid.  */
		    if (insert_regs (src, classp, 0))
		      {
			rehash_using_reg (src);
			sets[i].src_hash = HASH (src, mode);
		      }
		    elt = insert (src, classp, sets[i].src_hash, mode);
		    elt->in_memory = sets[i].src_in_memory;
		    sets[i].src_elt = classp = elt;
		  }
		else
		  sets[i].src_elt = classp;
	      }
	    if (sets[i].src_const && sets[i].src_const_elt == 0
		&& src != sets[i].src_const
		&& ! rtx_equal_p (sets[i].src_const, src))
	      sets[i].src_elt = insert (sets[i].src_const, classp,
					sets[i].src_const_hash, mode);
	  }
      }
    else if (sets[i].src_elt == 0)
      /* If we did not insert the source into the hash table (e.g., it was
	 volatile), note the equivalence class for the REG_EQUAL value, if any,
	 so that the destination goes into that class.  */
      sets[i].src_elt = src_eqv_elt;

  invalidate_from_clobbers (x);

  /* Some registers are invalidated by subroutine calls.  Memory is
     invalidated by non-constant calls.  */

  if (GET_CODE (insn) == CALL_INSN)
    {
      if (! CONST_OR_PURE_CALL_P (insn))
	invalidate_memory ();
      invalidate_for_call ();
    }

  /* Now invalidate everything set by this instruction.
     If a SUBREG or other funny destination is being set,
     sets[i].rtl is still nonzero, so here we invalidate the reg
     a part of which is being set.  */

  for (i = 0; i < n_sets; i++)
    if (sets[i].rtl)
      {
	/* We can't use the inner dest, because the mode associated with
	   a ZERO_EXTRACT is significant.  */
	rtx dest = SET_DEST (sets[i].rtl);

	/* Needed for registers to remove the register from its
	   previous quantity's chain.
	   Needed for memory if this is a nonvarying address, unless
	   we have just done an invalidate_memory that covers even those.  */
	if (GET_CODE (dest) == REG || GET_CODE (dest) == SUBREG)
	  invalidate (dest, VOIDmode);
	else if (GET_CODE (dest) == MEM)
	  {
	    /* Outgoing arguments for a libcall don't
	       affect any recorded expressions.  */
	    if (! libcall_insn || insn == libcall_insn)
	      invalidate (dest, VOIDmode);
	  }
	else if (GET_CODE (dest) == STRICT_LOW_PART
		 || GET_CODE (dest) == ZERO_EXTRACT)
	  invalidate (XEXP (dest, 0), GET_MODE (dest));
      }

  /* A volatile ASM invalidates everything.  */
  if (GET_CODE (insn) == INSN
      && GET_CODE (PATTERN (insn)) == ASM_OPERANDS
      && MEM_VOLATILE_P (PATTERN (insn)))
    flush_hash_table ();

  /* Make sure registers mentioned in destinations
     are safe for use in an expression to be inserted.
     This removes from the hash table
     any invalid entry that refers to one of these registers.

     We don't care about the return value from mention_regs because
     we are going to hash the SET_DEST values unconditionally.  */

  for (i = 0; i < n_sets; i++)
    {
      if (sets[i].rtl)
	{
	  rtx x = SET_DEST (sets[i].rtl);

	  if (GET_CODE (x) != REG)
	    mention_regs (x);
	  else
	    {
	      /* We used to rely on all references to a register becoming
		 inaccessible when a register changes to a new quantity,
		 since that changes the hash code.  However, that is not
		 safe, since after HASH_SIZE new quantities we get a
		 hash 'collision' of a register with its own invalid
		 entries.  And since SUBREGs have been changed not to
		 change their hash code with the hash code of the register,
		 it wouldn't work any longer at all.  So we have to check
		 for any invalid references lying around now.
		 This code is similar to the REG case in mention_regs,
		 but it knows that reg_tick has been incremented, and
		 it leaves reg_in_table as -1 .  */
	      unsigned int regno = REGNO (x);
	      unsigned int endregno
		= regno + (regno >= FIRST_PSEUDO_REGISTER ? 1
			   : HARD_REGNO_NREGS (regno, GET_MODE (x)));
	      unsigned int i;

	      for (i = regno; i < endregno; i++)
		{
		  if (REG_IN_TABLE (i) >= 0)
		    {
		      remove_invalid_refs (i);
		      REG_IN_TABLE (i) = -1;
		    }
		}
	    }
	}
    }

  /* We may have just removed some of the src_elt's from the hash table.
     So replace each one with the current head of the same class.  */

  for (i = 0; i < n_sets; i++)
    if (sets[i].rtl)
      {
	if (sets[i].src_elt && sets[i].src_elt->first_same_value == 0)
	  /* If elt was removed, find current head of same class,
	     or 0 if nothing remains of that class.  */
	  {
	    struct table_elt *elt = sets[i].src_elt;

	    while (elt && elt->prev_same_value)
	      elt = elt->prev_same_value;

	    while (elt && elt->first_same_value == 0)
	      elt = elt->next_same_value;
	    sets[i].src_elt = elt ? elt->first_same_value : 0;
	  }
      }

  /* Now insert the destinations into their equivalence classes.  */

  for (i = 0; i < n_sets; i++)
    if (sets[i].rtl)
      {
	rtx dest = SET_DEST (sets[i].rtl);
	rtx inner_dest = sets[i].inner_dest;
	struct table_elt *elt;

	/* Don't record value if we are not supposed to risk allocating
	   floating-point values in registers that might be wider than
	   memory.  */
	if ((flag_float_store
	     && GET_CODE (dest) == MEM
	     && FLOAT_MODE_P (GET_MODE (dest)))
	    /* Don't record BLKmode values, because we don't know the
	       size of it, and can't be sure that other BLKmode values
	       have the same or smaller size.  */
	    || GET_MODE (dest) == BLKmode
	    /* Don't record values of destinations set inside a libcall block
	       since we might delete the libcall.  Things should have been set
	       up so we won't want to reuse such a value, but we play it safe
	       here.  */
	    || libcall_insn
	    /* If we didn't put a REG_EQUAL value or a source into the hash
	       table, there is no point is recording DEST.  */
	    || sets[i].src_elt == 0
	    /* If DEST is a paradoxical SUBREG and SRC is a ZERO_EXTEND
	       or SIGN_EXTEND, don't record DEST since it can cause
	       some tracking to be wrong.

	       ??? Think about this more later.  */
	    || (GET_CODE (dest) == SUBREG
		&& (GET_MODE_SIZE (GET_MODE (dest))
		    > GET_MODE_SIZE (GET_MODE (SUBREG_REG (dest))))
		&& (GET_CODE (sets[i].src) == SIGN_EXTEND
		    || GET_CODE (sets[i].src) == ZERO_EXTEND)))
	  continue;

	/* STRICT_LOW_PART isn't part of the value BEING set,
	   and neither is the SUBREG inside it.
	   Note that in this case SETS[I].SRC_ELT is really SRC_EQV_ELT.  */
	if (GET_CODE (dest) == STRICT_LOW_PART)
	  dest = SUBREG_REG (XEXP (dest, 0));

	if (GET_CODE (dest) == REG || GET_CODE (dest) == SUBREG)
	  /* Registers must also be inserted into chains for quantities.  */
	  if (insert_regs (dest, sets[i].src_elt, 1))
	    {
	      /* If `insert_regs' changes something, the hash code must be
		 recalculated.  */
	      rehash_using_reg (dest);
	      sets[i].dest_hash = HASH (dest, GET_MODE (dest));
	    }

	if (GET_CODE (inner_dest) == MEM
	    && GET_CODE (XEXP (inner_dest, 0)) == ADDRESSOF)
	  /* Given (SET (MEM (ADDRESSOF (X))) Y) we don't want to say
	     that (MEM (ADDRESSOF (X))) is equivalent to Y.
	     Consider the case in which the address of the MEM is
	     passed to a function, which alters the MEM.  Then, if we
	     later use Y instead of the MEM we'll miss the update.  */
	  elt = insert (dest, 0, sets[i].dest_hash, GET_MODE (dest));
	else
	  elt = insert (dest, sets[i].src_elt,
			sets[i].dest_hash, GET_MODE (dest));

	elt->in_memory = (GET_CODE (sets[i].inner_dest) == MEM
			  && (! RTX_UNCHANGING_P (sets[i].inner_dest)
			      || FIXED_BASE_PLUS_P (XEXP (sets[i].inner_dest,
							  0))));

	/* If we have (set (subreg:m1 (reg:m2 foo) 0) (bar:m1)), M1 is no
	   narrower than M2, and both M1 and M2 are the same number of words,
	   we are also doing (set (reg:m2 foo) (subreg:m2 (bar:m1) 0)) so
	   make that equivalence as well.

	   However, BAR may have equivalences for which gen_lowpart_if_possible
	   will produce a simpler value than gen_lowpart_if_possible applied to
	   BAR (e.g., if BAR was ZERO_EXTENDed from M2), so we will scan all
	   BAR's equivalences.  If we don't get a simplified form, make
	   the SUBREG.  It will not be used in an equivalence, but will
	   cause two similar assignments to be detected.

	   Note the loop below will find SUBREG_REG (DEST) since we have
	   already entered SRC and DEST of the SET in the table.  */

	if (GET_CODE (dest) == SUBREG
	    && (((GET_MODE_SIZE (GET_MODE (SUBREG_REG (dest))) - 1)
		 / UNITS_PER_WORD)
		== (GET_MODE_SIZE (GET_MODE (dest)) - 1) / UNITS_PER_WORD)
	    && (GET_MODE_SIZE (GET_MODE (dest))
		>= GET_MODE_SIZE (GET_MODE (SUBREG_REG (dest))))
	    && sets[i].src_elt != 0)
	  {
	    enum machine_mode new_mode = GET_MODE (SUBREG_REG (dest));
	    struct table_elt *elt, *classp = 0;

	    for (elt = sets[i].src_elt->first_same_value; elt;
		 elt = elt->next_same_value)
	      {
		rtx new_src = 0;
		unsigned src_hash;
		struct table_elt *src_elt;
		int byte = 0;

		/* Ignore invalid entries.  */
		if (GET_CODE (elt->exp) != REG
		    && ! exp_equiv_p (elt->exp, elt->exp, 1, 0))
		  continue;

		/* We may have already been playing subreg games.  If the
		   mode is already correct for the destination, use it.  */
		if (GET_MODE (elt->exp) == new_mode)
		  new_src = elt->exp;
		else
		  {
		    /* Calculate big endian correction for the SUBREG_BYTE.
		       We have already checked that M1 (GET_MODE (dest))
		       is not narrower than M2 (new_mode).  */
		    if (BYTES_BIG_ENDIAN)
		      byte = (GET_MODE_SIZE (GET_MODE (dest))
			      - GET_MODE_SIZE (new_mode));

		    new_src = simplify_gen_subreg (new_mode, elt->exp,
					           GET_MODE (dest), byte);
		  }

		/* The call to simplify_gen_subreg fails if the value
		   is VOIDmode, yet we can't do any simplification, e.g.
		   for EXPR_LISTs denoting function call results.
		   It is invalid to construct a SUBREG with a VOIDmode
		   SUBREG_REG, hence a zero new_src means we can't do
		   this substitution.  */
		if (! new_src)
		  continue;

		src_hash = HASH (new_src, new_mode);
		src_elt = lookup (new_src, src_hash, new_mode);

		/* Put the new source in the hash table is if isn't
		   already.  */
		if (src_elt == 0)
		  {
		    if (insert_regs (new_src, classp, 0))
		      {
			rehash_using_reg (new_src);
			src_hash = HASH (new_src, new_mode);
		      }
		    src_elt = insert (new_src, classp, src_hash, new_mode);
		    src_elt->in_memory = elt->in_memory;
		  }
		else if (classp && classp != src_elt->first_same_value)
		  /* Show that two things that we've seen before are
		     actually the same.  */
		  merge_equiv_classes (src_elt, classp);

		classp = src_elt->first_same_value;
		/* Ignore invalid entries.  */
		while (classp
		       && GET_CODE (classp->exp) != REG
		       && ! exp_equiv_p (classp->exp, classp->exp, 1, 0))
		  classp = classp->next_same_value;
	      }
	  }
      }

  /* Special handling for (set REG0 REG1) where REG0 is the
     "cheapest", cheaper than REG1.  After cse, REG1 will probably not
     be used in the sequel, so (if easily done) change this insn to
     (set REG1 REG0) and replace REG1 with REG0 in the previous insn
     that computed their value.  Then REG1 will become a dead store
     and won't cloud the situation for later optimizations.

     Do not make this change if REG1 is a hard register, because it will
     then be used in the sequel and we may be changing a two-operand insn
     into a three-operand insn.

     Also do not do this if we are operating on a copy of INSN.

     Also don't do this if INSN ends a libcall; this would cause an unrelated
     register to be set in the middle of a libcall, and we then get bad code
     if the libcall is deleted.  */

  if (n_sets == 1 && sets[0].rtl && GET_CODE (SET_DEST (sets[0].rtl)) == REG
      && NEXT_INSN (PREV_INSN (insn)) == insn
      && GET_CODE (SET_SRC (sets[0].rtl)) == REG
      && REGNO (SET_SRC (sets[0].rtl)) >= FIRST_PSEUDO_REGISTER
      && REGNO_QTY_VALID_P (REGNO (SET_SRC (sets[0].rtl))))
    {
      int src_q = REG_QTY (REGNO (SET_SRC (sets[0].rtl)));
      struct qty_table_elem *src_ent = &qty_table[src_q];

      if ((src_ent->first_reg == REGNO (SET_DEST (sets[0].rtl)))
	  && ! find_reg_note (insn, REG_RETVAL, NULL_RTX))
	{
	  rtx prev = insn;
	  /* Scan for the previous nonnote insn, but stop at a basic
	     block boundary.  */
	  do
	    {
	      prev = PREV_INSN (prev);
	    }
	  while (prev && GET_CODE (prev) == NOTE
		 && NOTE_LINE_NUMBER (prev) != NOTE_INSN_BASIC_BLOCK);
	    
	  /* Do not swap the registers around if the previous instruction
	     attaches a REG_EQUIV note to REG1.

	     ??? It's not entirely clear whether we can transfer a REG_EQUIV
	     from the pseudo that originally shadowed an incoming argument
	     to another register.  Some uses of REG_EQUIV might rely on it
	     being attached to REG1 rather than REG2.

	     This section previously turned the REG_EQUIV into a REG_EQUAL
	     note.  We cannot do that because REG_EQUIV may provide an
	     uninitialized stack slot when REG_PARM_STACK_SPACE is used.  */

	  if (prev != 0 && GET_CODE (prev) == INSN
	      && GET_CODE (PATTERN (prev)) == SET
	      && SET_DEST (PATTERN (prev)) == SET_SRC (sets[0].rtl)
	      && ! find_reg_note (prev, REG_EQUIV, NULL_RTX))
	    {
	      rtx dest = SET_DEST (sets[0].rtl);
	      rtx src = SET_SRC (sets[0].rtl);
	      rtx note;

	      validate_change (prev, &SET_DEST (PATTERN (prev)), dest, 1);
	      validate_change (insn, &SET_DEST (sets[0].rtl), src, 1);
	      validate_change (insn, &SET_SRC (sets[0].rtl), dest, 1);
	      apply_change_group ();

	      /* If there was a REG_WAS_0 note on PREV, remove it.  Move
		 any REG_WAS_0 note on INSN to PREV.  */
	      note = find_reg_note (prev, REG_WAS_0, NULL_RTX);
	      if (note)
		remove_note (prev, note);

	      note = find_reg_note (insn, REG_WAS_0, NULL_RTX);
	      if (note)
		{
		  remove_note (insn, note);
		  XEXP (note, 1) = REG_NOTES (prev);
		  REG_NOTES (prev) = note;
		}

	      /* If INSN has a REG_EQUAL note, and this note mentions
		 REG0, then we must delete it, because the value in
		 REG0 has changed.  If the note's value is REG1, we must
		 also delete it because that is now this insn's dest.  */
	      note = find_reg_note (insn, REG_EQUAL, NULL_RTX);
	      if (note != 0
		  && (reg_mentioned_p (dest, XEXP (note, 0))
		      || rtx_equal_p (src, XEXP (note, 0))))
		remove_note (insn, note);
	    }
	}
    }

  /* If this is a conditional jump insn, record any known equivalences due to
     the condition being tested.  */

  last_jump_equiv_class = 0;
  if (GET_CODE (insn) == JUMP_INSN
      && n_sets == 1 && GET_CODE (x) == SET
      && GET_CODE (SET_SRC (x)) == IF_THEN_ELSE)
    record_jump_equiv (insn, 0);

#ifdef HAVE_cc0
  /* If the previous insn set CC0 and this insn no longer references CC0,
     delete the previous insn.  Here we use the fact that nothing expects CC0
     to be valid over an insn, which is true until the final pass.  */
  if (prev_insn && GET_CODE (prev_insn) == INSN
      && (tem = single_set (prev_insn)) != 0
      && SET_DEST (tem) == cc0_rtx
      && ! reg_mentioned_p (cc0_rtx, x))
    delete_insn (prev_insn);

  prev_insn_cc0 = this_insn_cc0;
  prev_insn_cc0_mode = this_insn_cc0_mode;
#endif

  prev_insn = insn;
}

/* Remove from the hash table all expressions that reference memory.  */

static void
invalidate_memory ()
{
  int i;
  struct table_elt *p, *next;

  for (i = 0; i < HASH_SIZE; i++)
    for (p = table[i]; p; p = next)
      {
	next = p->next_same_hash;
	if (p->in_memory)
	  remove_from_table (p, i);
      }
}

/* If ADDR is an address that implicitly affects the stack pointer, return
   1 and update the register tables to show the effect.  Else, return 0.  */

static int
addr_affects_sp_p (addr)
     rtx addr;
{
  if (GET_RTX_CLASS (GET_CODE (addr)) == 'a'
      && GET_CODE (XEXP (addr, 0)) == REG
      && REGNO (XEXP (addr, 0)) == STACK_POINTER_REGNUM)
    {
      if (REG_TICK (STACK_POINTER_REGNUM) >= 0)
	{
	  REG_TICK (STACK_POINTER_REGNUM)++;
	  /* Is it possible to use a subreg of SP?  */
	  SUBREG_TICKED (STACK_POINTER_REGNUM) = -1;
	}

      /* This should be *very* rare.  */
      if (TEST_HARD_REG_BIT (hard_regs_in_table, STACK_POINTER_REGNUM))
	invalidate (stack_pointer_rtx, VOIDmode);

      return 1;
    }

  return 0;
}

/* Perform invalidation on the basis of everything about an insn
   except for invalidating the actual places that are SET in it.
   This includes the places CLOBBERed, and anything that might
   alias with something that is SET or CLOBBERed.

   X is the pattern of the insn.  */

static void
invalidate_from_clobbers (x)
     rtx x;
{
  if (GET_CODE (x) == CLOBBER)
    {
      rtx ref = XEXP (x, 0);
      if (ref)
	{
	  if (GET_CODE (ref) == REG || GET_CODE (ref) == SUBREG
	      || GET_CODE (ref) == MEM)
	    invalidate (ref, VOIDmode);
	  else if (GET_CODE (ref) == STRICT_LOW_PART
		   || GET_CODE (ref) == ZERO_EXTRACT)
	    invalidate (XEXP (ref, 0), GET_MODE (ref));
	}
    }
  else if (GET_CODE (x) == PARALLEL)
    {
      int i;
      for (i = XVECLEN (x, 0) - 1; i >= 0; i--)
	{
	  rtx y = XVECEXP (x, 0, i);
	  if (GET_CODE (y) == CLOBBER)
	    {
	      rtx ref = XEXP (y, 0);
	      if (GET_CODE (ref) == REG || GET_CODE (ref) == SUBREG
		  || GET_CODE (ref) == MEM)
		invalidate (ref, VOIDmode);
	      else if (GET_CODE (ref) == STRICT_LOW_PART
		       || GET_CODE (ref) == ZERO_EXTRACT)
		invalidate (XEXP (ref, 0), GET_MODE (ref));
	    }
	}
    }
}

/* Process X, part of the REG_NOTES of an insn.  Look at any REG_EQUAL notes
   and replace any registers in them with either an equivalent constant
   or the canonical form of the register.  If we are inside an address,
   only do this if the address remains valid.

   OBJECT is 0 except when within a MEM in which case it is the MEM.

   Return the replacement for X.  */

static rtx
cse_process_notes (x, object)
     rtx x;
     rtx object;
{
  enum rtx_code code = GET_CODE (x);
  const char *fmt = GET_RTX_FORMAT (code);
  int i;

  switch (code)
    {
    case CONST_INT:
    case CONST:
    case SYMBOL_REF:
    case LABEL_REF:
    case CONST_DOUBLE:
    case CONST_VECTOR:
    case PC:
    case CC0:
    case LO_SUM:
      return x;

    case MEM:
      validate_change (x, &XEXP (x, 0),
		       cse_process_notes (XEXP (x, 0), x), 0);
      return x;

    case EXPR_LIST:
    case INSN_LIST:
      if (REG_NOTE_KIND (x) == REG_EQUAL)
	XEXP (x, 0) = cse_process_notes (XEXP (x, 0), NULL_RTX);
      if (XEXP (x, 1))
	XEXP (x, 1) = cse_process_notes (XEXP (x, 1), NULL_RTX);
      return x;

    case SIGN_EXTEND:
    case ZERO_EXTEND:
    case SUBREG:
      {
	rtx new = cse_process_notes (XEXP (x, 0), object);
	/* We don't substitute VOIDmode constants into these rtx,
	   since they would impede folding.  */
	if (GET_MODE (new) != VOIDmode)
	  validate_change (object, &XEXP (x, 0), new, 0);
	return x;
      }

    case REG:
      i = REG_QTY (REGNO (x));

      /* Return a constant or a constant register.  */
      if (REGNO_QTY_VALID_P (REGNO (x)))
	{
	  struct qty_table_elem *ent = &qty_table[i];

	  if (ent->const_rtx != NULL_RTX
	      && (CONSTANT_P (ent->const_rtx)
		  || GET_CODE (ent->const_rtx) == REG))
	    {
	      rtx new = gen_lowpart_if_possible (GET_MODE (x), ent->const_rtx);
	      if (new)
		return new;
	    }
	}

      /* Otherwise, canonicalize this register.  */
      return canon_reg (x, NULL_RTX);

    default:
      break;
    }

  for (i = 0; i < GET_RTX_LENGTH (code); i++)
    if (fmt[i] == 'e')
      validate_change (object, &XEXP (x, i),
		       cse_process_notes (XEXP (x, i), object), 0);

  return x;
}

/* Find common subexpressions between the end test of a loop and the beginning
   of the loop.  LOOP_START is the CODE_LABEL at the start of a loop.

   Often we have a loop where an expression in the exit test is used
   in the body of the loop.  For example "while (*p) *q++ = *p++;".
   Because of the way we duplicate the loop exit test in front of the loop,
   however, we don't detect that common subexpression.  This will be caught
   when global cse is implemented, but this is a quite common case.

   This function handles the most common cases of these common expressions.
   It is called after we have processed the basic block ending with the
   NOTE_INSN_LOOP_END note that ends a loop and the previous JUMP_INSN
   jumps to a label used only once.  */

static void
cse_around_loop (loop_start)
     rtx loop_start;
{
  rtx insn;
  int i;
  struct table_elt *p;

  /* If the jump at the end of the loop doesn't go to the start, we don't
     do anything.  */
  for (insn = PREV_INSN (loop_start);
       insn && (GET_CODE (insn) == NOTE && NOTE_LINE_NUMBER (insn) >= 0);
       insn = PREV_INSN (insn))
    ;

  if (insn == 0
      || GET_CODE (insn) != NOTE
      || NOTE_LINE_NUMBER (insn) != NOTE_INSN_LOOP_BEG)
    return;

  /* If the last insn of the loop (the end test) was an NE comparison,
     we will interpret it as an EQ comparison, since we fell through
     the loop.  Any equivalences resulting from that comparison are
     therefore not valid and must be invalidated.  */
  if (last_jump_equiv_class)
    for (p = last_jump_equiv_class->first_same_value; p;
	 p = p->next_same_value)
      {
	if (GET_CODE (p->exp) == MEM || GET_CODE (p->exp) == REG
	    || (GET_CODE (p->exp) == SUBREG
		&& GET_CODE (SUBREG_REG (p->exp)) == REG))
	  invalidate (p->exp, VOIDmode);
	else if (GET_CODE (p->exp) == STRICT_LOW_PART
		 || GET_CODE (p->exp) == ZERO_EXTRACT)
	  invalidate (XEXP (p->exp, 0), GET_MODE (p->exp));
      }

  /* Process insns starting after LOOP_START until we hit a CALL_INSN or
     a CODE_LABEL (we could handle a CALL_INSN, but it isn't worth it).

     The only thing we do with SET_DEST is invalidate entries, so we
     can safely process each SET in order.  It is slightly less efficient
     to do so, but we only want to handle the most common cases.

     The gen_move_insn call in cse_set_around_loop may create new pseudos.
     These pseudos won't have valid entries in any of the tables indexed
     by register number, such as reg_qty.  We avoid out-of-range array
     accesses by not processing any instructions created after cse started.  */

  for (insn = NEXT_INSN (loop_start);
       GET_CODE (insn) != CALL_INSN && GET_CODE (insn) != CODE_LABEL
       && INSN_UID (insn) < max_insn_uid
       && ! (GET_CODE (insn) == NOTE
	     && NOTE_LINE_NUMBER (insn) == NOTE_INSN_LOOP_END);
       insn = NEXT_INSN (insn))
    {
      if (INSN_P (insn)
	  && (GET_CODE (PATTERN (insn)) == SET
	      || GET_CODE (PATTERN (insn)) == CLOBBER))
	cse_set_around_loop (PATTERN (insn), insn, loop_start);
      else if (INSN_P (insn) && GET_CODE (PATTERN (insn)) == PARALLEL)
	for (i = XVECLEN (PATTERN (insn), 0) - 1; i >= 0; i--)
	  if (GET_CODE (XVECEXP (PATTERN (insn), 0, i)) == SET
	      || GET_CODE (XVECEXP (PATTERN (insn), 0, i)) == CLOBBER)
	    cse_set_around_loop (XVECEXP (PATTERN (insn), 0, i), insn,
				 loop_start);
    }
}

/* Process one SET of an insn that was skipped.  We ignore CLOBBERs
   since they are done elsewhere.  This function is called via note_stores.  */

static void
invalidate_skipped_set (dest, set, data)
     rtx set;
     rtx dest;
     void *data ATTRIBUTE_UNUSED;
{
  enum rtx_code code = GET_CODE (dest);

  if (code == MEM
      && ! addr_affects_sp_p (dest)	/* If this is not a stack push ...  */
      /* There are times when an address can appear varying and be a PLUS
	 during this scan when it would be a fixed address were we to know
	 the proper equivalences.  So invalidate all memory if there is
	 a BLKmode or nonscalar memory reference or a reference to a
	 variable address.  */
      && (MEM_IN_STRUCT_P (dest) || GET_MODE (dest) == BLKmode
	  || cse_rtx_varies_p (XEXP (dest, 0), 0)))
    {
      invalidate_memory ();
      return;
    }

  if (GET_CODE (set) == CLOBBER
#ifdef HAVE_cc0
      || dest == cc0_rtx
#endif
      || dest == pc_rtx)
    return;

  if (code == STRICT_LOW_PART || code == ZERO_EXTRACT)
    invalidate (XEXP (dest, 0), GET_MODE (dest));
  else if (code == REG || code == SUBREG || code == MEM)
    invalidate (dest, VOIDmode);
}

/* Invalidate all insns from START up to the end of the function or the
   next label.  This called when we wish to CSE around a block that is
   conditionally executed.  */

static void
invalidate_skipped_block (start)
     rtx start;
{
  rtx insn;

  for (insn = start; insn && GET_CODE (insn) != CODE_LABEL;
       insn = NEXT_INSN (insn))
    {
      if (! INSN_P (insn))
	continue;

      if (GET_CODE (insn) == CALL_INSN)
	{
	  if (! CONST_OR_PURE_CALL_P (insn))
	    invalidate_memory ();
	  invalidate_for_call ();
	}

      invalidate_from_clobbers (PATTERN (insn));
      note_stores (PATTERN (insn), invalidate_skipped_set, NULL);
    }
}

/* If modifying X will modify the value in *DATA (which is really an
   `rtx *'), indicate that fact by setting the pointed to value to
   NULL_RTX.  */

static void
cse_check_loop_start (x, set, data)
     rtx x;
     rtx set ATTRIBUTE_UNUSED;
     void *data;
{
  rtx *cse_check_loop_start_value = (rtx *) data;

  if (*cse_check_loop_start_value == NULL_RTX
      || GET_CODE (x) == CC0 || GET_CODE (x) == PC)
    return;

  if ((GET_CODE (x) == MEM && GET_CODE (*cse_check_loop_start_value) == MEM)
      || reg_overlap_mentioned_p (x, *cse_check_loop_start_value))
    *cse_check_loop_start_value = NULL_RTX;
}

/* X is a SET or CLOBBER contained in INSN that was found near the start of
   a loop that starts with the label at LOOP_START.

   If X is a SET, we see if its SET_SRC is currently in our hash table.
   If so, we see if it has a value equal to some register used only in the
   loop exit code (as marked by jump.c).

   If those two conditions are true, we search backwards from the start of
   the loop to see if that same value was loaded into a register that still
   retains its value at the start of the loop.

   If so, we insert an insn after the load to copy the destination of that
   load into the equivalent register and (try to) replace our SET_SRC with that
   register.

   In any event, we invalidate whatever this SET or CLOBBER modifies.  */

static void
cse_set_around_loop (x, insn, loop_start)
     rtx x;
     rtx insn;
     rtx loop_start;
{
  struct table_elt *src_elt;

  /* If this is a SET, see if we can replace SET_SRC, but ignore SETs that
     are setting PC or CC0 or whose SET_SRC is already a register.  */
  if (GET_CODE (x) == SET
      && GET_CODE (SET_DEST (x)) != PC && GET_CODE (SET_DEST (x)) != CC0
      && GET_CODE (SET_SRC (x)) != REG)
    {
      src_elt = lookup (SET_SRC (x),
			HASH (SET_SRC (x), GET_MODE (SET_DEST (x))),
			GET_MODE (SET_DEST (x)));

      if (src_elt)
	for (src_elt = src_elt->first_same_value; src_elt;
	     src_elt = src_elt->next_same_value)
	  if (GET_CODE (src_elt->exp) == REG && REG_LOOP_TEST_P (src_elt->exp)
	      && COST (src_elt->exp) < COST (SET_SRC (x)))
	    {
	      rtx p, set;

	      /* Look for an insn in front of LOOP_START that sets
		 something in the desired mode to SET_SRC (x) before we hit
		 a label or CALL_INSN.  */

	      for (p = prev_nonnote_insn (loop_start);
		   p && GET_CODE (p) != CALL_INSN
		   && GET_CODE (p) != CODE_LABEL;
		   p = prev_nonnote_insn  (p))
		if ((set = single_set (p)) != 0
		    && GET_CODE (SET_DEST (set)) == REG
		    && GET_MODE (SET_DEST (set)) == src_elt->mode
		    && rtx_equal_p (SET_SRC (set), SET_SRC (x)))
		  {
		    /* We now have to ensure that nothing between P
		       and LOOP_START modified anything referenced in
		       SET_SRC (x).  We know that nothing within the loop
		       can modify it, or we would have invalidated it in
		       the hash table.  */
		    rtx q;
		    rtx cse_check_loop_start_value = SET_SRC (x);
		    for (q = p; q != loop_start; q = NEXT_INSN (q))
		      if (INSN_P (q))
			note_stores (PATTERN (q),
				     cse_check_loop_start,
				     &cse_check_loop_start_value);

		    /* If nothing was changed and we can replace our
		       SET_SRC, add an insn after P to copy its destination
		       to what we will be replacing SET_SRC with.  */
		    if (cse_check_loop_start_value
			&& validate_change (insn, &SET_SRC (x),
					    src_elt->exp, 0))
		      {
			/* If this creates new pseudos, this is unsafe,
			   because the regno of new pseudo is unsuitable
			   to index into reg_qty when cse_insn processes
			   the new insn.  Therefore, if a new pseudo was
			   created, discard this optimization.  */
			int nregs = max_reg_num ();
			rtx move
			  = gen_move_insn (src_elt->exp, SET_DEST (set));
			if (nregs != max_reg_num ())
			  {
			    if (! validate_change (insn, &SET_SRC (x),
						   SET_SRC (set), 0))
			      abort ();
			  }
			else
			  {
			    if (control_flow_insn_p (p))
			      /* p can cause a control flow transfer so it
				 is the last insn of a basic block.  We can't
				 therefore use emit_insn_after.  */
			      emit_insn_before (move, next_nonnote_insn (p));
			    else
			      emit_insn_after (move, p);
			  }
		      }
		    break;
		  }
	    }
    }

  /* Deal with the destination of X affecting the stack pointer.  */
  addr_affects_sp_p (SET_DEST (x));

  /* See comment on similar code in cse_insn for explanation of these
     tests.  */
  if (GET_CODE (SET_DEST (x)) == REG || GET_CODE (SET_DEST (x)) == SUBREG
      || GET_CODE (SET_DEST (x)) == MEM)
    invalidate (SET_DEST (x), VOIDmode);
  else if (GET_CODE (SET_DEST (x)) == STRICT_LOW_PART
	   || GET_CODE (SET_DEST (x)) == ZERO_EXTRACT)
    invalidate (XEXP (SET_DEST (x), 0), GET_MODE (SET_DEST (x)));
}

/* Find the end of INSN's basic block and return its range,
   the total number of SETs in all the insns of the block, the last insn of the
   block, and the branch path.

   The branch path indicates which branches should be followed.  If a nonzero
   path size is specified, the block should be rescanned and a different set
   of branches will be taken.  The branch path is only used if
   FLAG_CSE_FOLLOW_JUMPS or FLAG_CSE_SKIP_BLOCKS is nonzero.

   DATA is a pointer to a struct cse_basic_block_data, defined below, that is
   used to describe the block.  It is filled in with the information about
   the current block.  The incoming structure's branch path, if any, is used
   to construct the output branch path.  */

void
cse_end_of_basic_block (insn, data, follow_jumps, after_loop, skip_blocks)
     rtx insn;
     struct cse_basic_block_data *data;
     int follow_jumps;
     int after_loop;
     int skip_blocks;
{
  rtx p = insn, q;
  int nsets = 0;
  int low_cuid = INSN_CUID (insn), high_cuid = INSN_CUID (insn);
  rtx next = INSN_P (insn) ? insn : next_real_insn (insn);
  int path_size = data->path_size;
  int path_entry = 0;
  int i;

  /* Update the previous branch path, if any.  If the last branch was
     previously TAKEN, mark it NOT_TAKEN.  If it was previously NOT_TAKEN,
     shorten the path by one and look at the previous branch.  We know that
     at least one branch must have been taken if PATH_SIZE is nonzero.  */
  while (path_size > 0)
    {
      if (data->path[path_size - 1].status != NOT_TAKEN)
	{
	  data->path[path_size - 1].status = NOT_TAKEN;
	  break;
	}
      else
	path_size--;
    }

  /* If the first instruction is marked with QImode, that means we've
     already processed this block.  Our caller will look at DATA->LAST
     to figure out where to go next.  We want to return the next block
     in the instruction stream, not some branched-to block somewhere
     else.  We accomplish this by pretending our called forbid us to
     follow jumps, or skip blocks.  */
  if (GET_MODE (insn) == QImode)
    follow_jumps = skip_blocks = 0;

  /* Scan to end of this basic block.  */
  while (p && GET_CODE (p) != CODE_LABEL)
    {
      /* Don't cse out the end of a loop.  This makes a difference
	 only for the unusual loops that always execute at least once;
	 all other loops have labels there so we will stop in any case.
	 Cse'ing out the end of the loop is dangerous because it
	 might cause an invariant expression inside the loop
	 to be reused after the end of the loop.  This would make it
	 hard to move the expression out of the loop in loop.c,
	 especially if it is one of several equivalent expressions
	 and loop.c would like to eliminate it.

	 If we are running after loop.c has finished, we can ignore
	 the NOTE_INSN_LOOP_END.  */

      if (! after_loop && GET_CODE (p) == NOTE
	  && NOTE_LINE_NUMBER (p) == NOTE_INSN_LOOP_END)
	break;

      /* Don't cse over a call to setjmp; on some machines (eg VAX)
	 the regs restored by the longjmp come from
	 a later time than the setjmp.  */
      if (PREV_INSN (p) && GET_CODE (PREV_INSN (p)) == CALL_INSN
	  && find_reg_note (PREV_INSN (p), REG_SETJMP, NULL))
	break;

      /* A PARALLEL can have lots of SETs in it,
	 especially if it is really an ASM_OPERANDS.  */
      if (INSN_P (p) && GET_CODE (PATTERN (p)) == PARALLEL)
	nsets += XVECLEN (PATTERN (p), 0);
      else if (GET_CODE (p) != NOTE)
	nsets += 1;

      /* Ignore insns made by CSE; they cannot affect the boundaries of
	 the basic block.  */

      if (INSN_UID (p) <= max_uid && INSN_CUID (p) > high_cuid)
	high_cuid = INSN_CUID (p);
      if (INSN_UID (p) <= max_uid && INSN_CUID (p) < low_cuid)
	low_cuid = INSN_CUID (p);

      /* See if this insn is in our branch path.  If it is and we are to
	 take it, do so.  */
      if (path_entry < path_size && data->path[path_entry].branch == p)
	{
	  if (data->path[path_entry].status != NOT_TAKEN)
	    p = JUMP_LABEL (p);

	  /* Point to next entry in path, if any.  */
	  path_entry++;
	}

      /* If this is a conditional jump, we can follow it if -fcse-follow-jumps
	 was specified, we haven't reached our maximum path length, there are
	 insns following the target of the jump, this is the only use of the
	 jump label, and the target label is preceded by a BARRIER.

	 Alternatively, we can follow the jump if it branches around a
	 block of code and there are no other branches into the block.
	 In this case invalidate_skipped_block will be called to invalidate any
	 registers set in the block when following the jump.  */

      else if ((follow_jumps || skip_blocks) && path_size < PATHLENGTH - 1
	       && GET_CODE (p) == JUMP_INSN
	       && GET_CODE (PATTERN (p)) == SET
	       && GET_CODE (SET_SRC (PATTERN (p))) == IF_THEN_ELSE
	       && JUMP_LABEL (p) != 0
	       && LABEL_NUSES (JUMP_LABEL (p)) == 1
	       && NEXT_INSN (JUMP_LABEL (p)) != 0)
	{
	  for (q = PREV_INSN (JUMP_LABEL (p)); q; q = PREV_INSN (q))
	    if ((GET_CODE (q) != NOTE
		 || NOTE_LINE_NUMBER (q) == NOTE_INSN_LOOP_END
		 || (PREV_INSN (q) && GET_CODE (PREV_INSN (q)) == CALL_INSN
		     && find_reg_note (PREV_INSN (q), REG_SETJMP, NULL)))
		&& (GET_CODE (q) != CODE_LABEL || LABEL_NUSES (q) != 0))
	      break;

	  /* If we ran into a BARRIER, this code is an extension of the
	     basic block when the branch is taken.  */
	  if (follow_jumps && q != 0 && GET_CODE (q) == BARRIER)
	    {
	      /* Don't allow ourself to keep walking around an
		 always-executed loop.  */
	      if (next_real_insn (q) == next)
		{
		  p = NEXT_INSN (p);
		  continue;
		}

	      /* Similarly, don't put a branch in our path more than once.  */
	      for (i = 0; i < path_entry; i++)
		if (data->path[i].branch == p)
		  break;

	      if (i != path_entry)
		break;

	      data->path[path_entry].branch = p;
	      data->path[path_entry++].status = TAKEN;

	      /* This branch now ends our path.  It was possible that we
		 didn't see this branch the last time around (when the
		 insn in front of the target was a JUMP_INSN that was
		 turned into a no-op).  */
	      path_size = path_entry;

	      p = JUMP_LABEL (p);
	      /* Mark block so we won't scan it again later.  */
	      PUT_MODE (NEXT_INSN (p), QImode);
	    }
	  /* Detect a branch around a block of code.  */
	  else if (skip_blocks && q != 0 && GET_CODE (q) != CODE_LABEL)
	    {
	      rtx tmp;

	      if (next_real_insn (q) == next)
		{
		  p = NEXT_INSN (p);
		  continue;
		}

	      for (i = 0; i < path_entry; i++)
		if (data->path[i].branch == p)
		  break;

	      if (i != path_entry)
		break;

	      /* This is no_labels_between_p (p, q) with an added check for
		 reaching the end of a function (in case Q precedes P).  */
	      for (tmp = NEXT_INSN (p); tmp && tmp != q; tmp = NEXT_INSN (tmp))
		if (GET_CODE (tmp) == CODE_LABEL)
		  break;

	      if (tmp == q)
		{
		  data->path[path_entry].branch = p;
		  data->path[path_entry++].status = AROUND;

		  path_size = path_entry;

		  p = JUMP_LABEL (p);
		  /* Mark block so we won't scan it again later.  */
		  PUT_MODE (NEXT_INSN (p), QImode);
		}
	    }
	}
      p = NEXT_INSN (p);
    }

  data->low_cuid = low_cuid;
  data->high_cuid = high_cuid;
  data->nsets = nsets;
  data->last = p;

  /* If all jumps in the path are not taken, set our path length to zero
     so a rescan won't be done.  */
  for (i = path_size - 1; i >= 0; i--)
    if (data->path[i].status != NOT_TAKEN)
      break;

  if (i == -1)
    data->path_size = 0;
  else
    data->path_size = path_size;

  /* End the current branch path.  */
  data->path[path_size].branch = 0;
}

/* Perform cse on the instructions of a function.
   F is the first instruction.
   NREGS is one plus the highest pseudo-reg number used in the instruction.

   AFTER_LOOP is 1 if this is the cse call done after loop optimization
   (only if -frerun-cse-after-loop).

   Returns 1 if jump_optimize should be redone due to simplifications
   in conditional jump instructions.  */

int
cse_main (f, nregs, after_loop, file)
     rtx f;
     int nregs;
     int after_loop;
     FILE *file;
{
  struct cse_basic_block_data val;
  rtx insn = f;
  int i;

  cse_jumps_altered = 0;
  recorded_label_ref = 0;
  constant_pool_entries_cost = 0;
  val.path_size = 0;

  init_recog ();
  init_alias_analysis ();

  max_reg = nregs;

  max_insn_uid = get_max_uid ();

  reg_eqv_table = (struct reg_eqv_elem *)
    xmalloc (nregs * sizeof (struct reg_eqv_elem));

#ifdef LOAD_EXTEND_OP

  /* Allocate scratch rtl here.  cse_insn will fill in the memory reference
     and change the code and mode as appropriate.  */
  memory_extend_rtx = gen_rtx_ZERO_EXTEND (VOIDmode, NULL_RTX);
#endif

  /* Reset the counter indicating how many elements have been made
     thus far.  */
  n_elements_made = 0;

  /* Find the largest uid.  */

  max_uid = get_max_uid ();
  uid_cuid = (int *) xcalloc (max_uid + 1, sizeof (int));

  /* Compute the mapping from uids to cuids.
     CUIDs are numbers assigned to insns, like uids,
     except that cuids increase monotonically through the code.
     Don't assign cuids to line-number NOTEs, so that the distance in cuids
     between two insns is not affected by -g.  */

  for (insn = f, i = 0; insn; insn = NEXT_INSN (insn))
    {
      if (GET_CODE (insn) != NOTE
	  || NOTE_LINE_NUMBER (insn) < 0)
	INSN_CUID (insn) = ++i;
      else
	/* Give a line number note the same cuid as preceding insn.  */
	INSN_CUID (insn) = i;
    }

  ggc_push_context ();

  /* Loop over basic blocks.
     Compute the maximum number of qty's needed for each basic block
     (which is 2 for each SET).  */
  insn = f;
  while (insn)
    {
      cse_altered = 0;
      cse_end_of_basic_block (insn, &val, flag_cse_follow_jumps, after_loop,
			      flag_cse_skip_blocks);

      /* If this basic block was already processed or has no sets, skip it.  */
      if (val.nsets == 0 || GET_MODE (insn) == QImode)
	{
	  PUT_MODE (insn, VOIDmode);
	  insn = (val.last ? NEXT_INSN (val.last) : 0);
	  val.path_size = 0;
	  continue;
	}

      cse_basic_block_start = val.low_cuid;
      cse_basic_block_end = val.high_cuid;
      max_qty = val.nsets * 2;

      if (file)
	fnotice (file, ";; Processing block from %d to %d, %d sets.\n",
		 INSN_UID (insn), val.last ? INSN_UID (val.last) : 0,
		 val.nsets);

      /* Make MAX_QTY bigger to give us room to optimize
	 past the end of this basic block, if that should prove useful.  */
      if (max_qty < 500)
	max_qty = 500;

      max_qty += max_reg;

      /* If this basic block is being extended by following certain jumps,
         (see `cse_end_of_basic_block'), we reprocess the code from the start.
         Otherwise, we start after this basic block.  */
      if (val.path_size > 0)
	cse_basic_block (insn, val.last, val.path, 0);
      else
	{
	  int old_cse_jumps_altered = cse_jumps_altered;
	  rtx temp;

	  /* When cse changes a conditional jump to an unconditional
	     jump, we want to reprocess the block, since it will give
	     us a new branch path to investigate.  */
	  cse_jumps_altered = 0;
	  temp = cse_basic_block (insn, val.last, val.path, ! after_loop);
	  if (cse_jumps_altered == 0
	      || (flag_cse_follow_jumps == 0 && flag_cse_skip_blocks == 0))
	    insn = temp;

	  cse_jumps_altered |= old_cse_jumps_altered;
	}

      if (cse_altered)
	ggc_collect ();

#ifdef USE_C_ALLOCA
      alloca (0);
#endif
    }

  ggc_pop_context ();

  if (max_elements_made < n_elements_made)
    max_elements_made = n_elements_made;

  /* Clean up.  */
  end_alias_analysis ();
  free (uid_cuid);
  free (reg_eqv_table);

  return cse_jumps_altered || recorded_label_ref;
}

/* Process a single basic block.  FROM and TO and the limits of the basic
   block.  NEXT_BRANCH points to the branch path when following jumps or
   a null path when not following jumps.

   AROUND_LOOP is nonzero if we are to try to cse around to the start of a
   loop.  This is true when we are being called for the last time on a
   block and this CSE pass is before loop.c.  */

static rtx
cse_basic_block (from, to, next_branch, around_loop)
     rtx from, to;
     struct branch_path *next_branch;
     int around_loop;
{
  rtx insn;
  int to_usage = 0;
  rtx libcall_insn = NULL_RTX;
  int num_insns = 0;

  /* This array is undefined before max_reg, so only allocate
     the space actually needed and adjust the start.  */

  qty_table
    = (struct qty_table_elem *) xmalloc ((max_qty - max_reg)
					 * sizeof (struct qty_table_elem));
  qty_table -= max_reg;

  new_basic_block ();

  /* TO might be a label.  If so, protect it from being deleted.  */
  if (to != 0 && GET_CODE (to) == CODE_LABEL)
    ++LABEL_NUSES (to);

  for (insn = from; insn != to; insn = NEXT_INSN (insn))
    {
      enum rtx_code code = GET_CODE (insn);

      /* If we have processed 1,000 insns, flush the hash table to
	 avoid extreme quadratic behavior.  We must not include NOTEs
	 in the count since there may be more of them when generating
	 debugging information.  If we clear the table at different
	 times, code generated with -g -O might be different than code
	 generated with -O but not -g.

	 ??? This is a real kludge and needs to be done some other way.
	 Perhaps for 2.9.  */
      if (code != NOTE && num_insns++ > 1000)
	{
	  flush_hash_table ();
	  num_insns = 0;
	}

      /* See if this is a branch that is part of the path.  If so, and it is
	 to be taken, do so.  */
      if (next_branch->branch == insn)
	{
	  enum taken status = next_branch++->status;
	  if (status != NOT_TAKEN)
	    {
	      if (status == TAKEN)
		record_jump_equiv (insn, 1);
	      else
		invalidate_skipped_block (NEXT_INSN (insn));

	      /* Set the last insn as the jump insn; it doesn't affect cc0.
		 Then follow this branch.  */
#ifdef HAVE_cc0
	      prev_insn_cc0 = 0;
#endif
	      prev_insn = insn;
	      insn = JUMP_LABEL (insn);
	      continue;
	    }
	}

      if (GET_MODE (insn) == QImode)
	PUT_MODE (insn, VOIDmode);

      if (GET_RTX_CLASS (code) == 'i')
	{
	  rtx p;

	  /* Process notes first so we have all notes in canonical forms when
	     looking for duplicate operations.  */

	  if (REG_NOTES (insn))
	    REG_NOTES (insn) = cse_process_notes (REG_NOTES (insn), NULL_RTX);

	  /* Track when we are inside in LIBCALL block.  Inside such a block,
	     we do not want to record destinations.  The last insn of a
	     LIBCALL block is not considered to be part of the block, since
	     its destination is the result of the block and hence should be
	     recorded.  */

	  if (REG_NOTES (insn) != 0)
	    {
	      if ((p = find_reg_note (insn, REG_LIBCALL, NULL_RTX)))
		libcall_insn = XEXP (p, 0);
	      else if (find_reg_note (insn, REG_RETVAL, NULL_RTX))
		libcall_insn = 0;
	    }

	  cse_insn (insn, libcall_insn);

	  /* If we haven't already found an insn where we added a LABEL_REF,
	     check this one.  */
	  if (GET_CODE (insn) == INSN && ! recorded_label_ref
	      && for_each_rtx (&PATTERN (insn), check_for_label_ref,
			       (void *) insn))
	    recorded_label_ref = 1;
	}

      /* If INSN is now an unconditional jump, skip to the end of our
	 basic block by pretending that we just did the last insn in the
	 basic block.  If we are jumping to the end of our block, show
	 that we can have one usage of TO.  */

      if (any_uncondjump_p (insn))
	{
	  if (to == 0)
	    {
	      free (qty_table + max_reg);
	      return 0;
	    }

	  if (JUMP_LABEL (insn) == to)
	    to_usage = 1;

	  /* Maybe TO was deleted because the jump is unconditional.
	     If so, there is nothing left in this basic block.  */
	  /* ??? Perhaps it would be smarter to set TO
	     to whatever follows this insn,
	     and pretend the basic block had always ended here.  */
	  if (INSN_DELETED_P (to))
	    break;

	  insn = PREV_INSN (to);
	}

      /* See if it is ok to keep on going past the label
	 which used to end our basic block.  Remember that we incremented
	 the count of that label, so we decrement it here.  If we made
	 a jump unconditional, TO_USAGE will be one; in that case, we don't
	 want to count the use in that jump.  */

      if (to != 0 && NEXT_INSN (insn) == to
	  && GET_CODE (to) == CODE_LABEL && --LABEL_NUSES (to) == to_usage)
	{
	  struct cse_basic_block_data val;
	  rtx prev;

	  insn = NEXT_INSN (to);

	  /* If TO was the last insn in the function, we are done.  */
	  if (insn == 0)
	    {
	      free (qty_table + max_reg);
	      return 0;
	    }

	  /* If TO was preceded by a BARRIER we are done with this block
	     because it has no continuation.  */
	  prev = prev_nonnote_insn (to);
	  if (prev && GET_CODE (prev) == BARRIER)
	    {
	      free (qty_table + max_reg);
	      return insn;
	    }

	  /* Find the end of the following block.  Note that we won't be
	     following branches in this case.  */
	  to_usage = 0;
	  val.path_size = 0;
	  cse_end_of_basic_block (insn, &val, 0, 0, 0);

	  /* If the tables we allocated have enough space left
	     to handle all the SETs in the next basic block,
	     continue through it.  Otherwise, return,
	     and that block will be scanned individually.  */
	  if (val.nsets * 2 + next_qty > max_qty)
	    break;

	  cse_basic_block_start = val.low_cuid;
	  cse_basic_block_end = val.high_cuid;
	  to = val.last;

	  /* Prevent TO from being deleted if it is a label.  */
	  if (to != 0 && GET_CODE (to) == CODE_LABEL)
	    ++LABEL_NUSES (to);

	  /* Back up so we process the first insn in the extension.  */
	  insn = PREV_INSN (insn);
	}
    }

  if (next_qty > max_qty)
    abort ();

  /* If we are running before loop.c, we stopped on a NOTE_INSN_LOOP_END, and
     the previous insn is the only insn that branches to the head of a loop,
     we can cse into the loop.  Don't do this if we changed the jump
     structure of a loop unless we aren't going to be following jumps.  */

  insn = prev_nonnote_insn (to);
  if ((cse_jumps_altered == 0
       || (flag_cse_follow_jumps == 0 && flag_cse_skip_blocks == 0))
      && around_loop && to != 0
      && GET_CODE (to) == NOTE && NOTE_LINE_NUMBER (to) == NOTE_INSN_LOOP_END
      && GET_CODE (insn) == JUMP_INSN
      && JUMP_LABEL (insn) != 0
      && LABEL_NUSES (JUMP_LABEL (insn)) == 1)
    cse_around_loop (JUMP_LABEL (insn));

  free (qty_table + max_reg);

  return to ? NEXT_INSN (to) : 0;
}

/* Called via for_each_rtx to see if an insn is using a LABEL_REF for which
   there isn't a REG_LABEL note.  Return one if so.  DATA is the insn.  */

static int
check_for_label_ref (rtl, data)
     rtx *rtl;
     void *data;
{
  rtx insn = (rtx) data;

  /* If this insn uses a LABEL_REF and there isn't a REG_LABEL note for it,
     we must rerun jump since it needs to place the note.  If this is a
     LABEL_REF for a CODE_LABEL that isn't in the insn chain, don't do this
     since no REG_LABEL will be added.  */
  return (GET_CODE (*rtl) == LABEL_REF
	  && ! LABEL_REF_NONLOCAL_P (*rtl)
	  && LABEL_P (XEXP (*rtl, 0))
	  && INSN_UID (XEXP (*rtl, 0)) != 0
	  && ! find_reg_note (insn, REG_LABEL, XEXP (*rtl, 0)));
}

/* Count the number of times registers are used (not set) in X.
   COUNTS is an array in which we accumulate the count, INCR is how much
   we count each register usage.

   Don't count a usage of DEST, which is the SET_DEST of a SET which
   contains X in its SET_SRC.  This is because such a SET does not
   modify the liveness of DEST.  */

static void
count_reg_usage (x, counts, dest, incr)
     rtx x;
     int *counts;
     rtx dest;
     int incr;
{
  enum rtx_code code;
  rtx note;
  const char *fmt;
  int i, j;

  if (x == 0)
    return;

  switch (code = GET_CODE (x))
    {
    case REG:
      if (x != dest)
	counts[REGNO (x)] += incr;
      return;

    case PC:
    case CC0:
    case CONST:
    case CONST_INT:
    case CONST_DOUBLE:
    case CONST_VECTOR:
    case SYMBOL_REF:
    case LABEL_REF:
      return;

    case CLOBBER:
      /* If we are clobbering a MEM, mark any registers inside the address
         as being used.  */
      if (GET_CODE (XEXP (x, 0)) == MEM)
	count_reg_usage (XEXP (XEXP (x, 0), 0), counts, NULL_RTX, incr);
      return;

    case SET:
      /* Unless we are setting a REG, count everything in SET_DEST.  */
      if (GET_CODE (SET_DEST (x)) != REG)
	count_reg_usage (SET_DEST (x), counts, NULL_RTX, incr);

      /* If SRC has side-effects, then we can't delete this insn, so the
	 usage of SET_DEST inside SRC counts.

	 ??? Strictly-speaking, we might be preserving this insn
	 because some other SET has side-effects, but that's hard
	 to do and can't happen now.  */
      count_reg_usage (SET_SRC (x), counts,
		       side_effects_p (SET_SRC (x)) ? NULL_RTX : SET_DEST (x),
		       incr);
      return;

    case CALL_INSN:
      count_reg_usage (CALL_INSN_FUNCTION_USAGE (x), counts, NULL_RTX, incr);
      /* Fall through.  */

    case INSN:
    case JUMP_INSN:
      count_reg_usage (PATTERN (x), counts, NULL_RTX, incr);

      /* Things used in a REG_EQUAL note aren't dead since loop may try to
	 use them.  */

      note = find_reg_equal_equiv_note (x);
      if (note)
        count_reg_usage (XEXP (note, 0), counts, NULL_RTX, incr);
      return;

    case INSN_LIST:
      abort ();

    default:
      break;
    }

  fmt = GET_RTX_FORMAT (code);
  for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--)
    {
      if (fmt[i] == 'e')
	count_reg_usage (XEXP (x, i), counts, dest, incr);
      else if (fmt[i] == 'E')
	for (j = XVECLEN (x, i) - 1; j >= 0; j--)
	  count_reg_usage (XVECEXP (x, i, j), counts, dest, incr);
    }
}

/* Return true if set is live.  */
static bool
set_live_p (set, insn, counts)
     rtx set;
     rtx insn ATTRIBUTE_UNUSED;	/* Only used with HAVE_cc0.  */
     int *counts;
{
#ifdef HAVE_cc0
  rtx tem;
#endif

  if (set_noop_p (set))
    ;

#ifdef HAVE_cc0
  else if (GET_CODE (SET_DEST (set)) == CC0
	   && !side_effects_p (SET_SRC (set))
	   && ((tem = next_nonnote_insn (insn)) == 0
	       || !INSN_P (tem)
	       || !reg_referenced_p (cc0_rtx, PATTERN (tem))))
    return false;
#endif
  else if (GET_CODE (SET_DEST (set)) != REG
	   || REGNO (SET_DEST (set)) < FIRST_PSEUDO_REGISTER
	   || counts[REGNO (SET_DEST (set))] != 0
	   || side_effects_p (SET_SRC (set))
	   /* An ADDRESSOF expression can turn into a use of the
	      internal arg pointer, so always consider the
	      internal arg pointer live.  If it is truly dead,
	      flow will delete the initializing insn.  */
	   || (SET_DEST (set) == current_function_internal_arg_pointer))
    return true;
  return false;
}

/* Return true if insn is live.  */

static bool
insn_live_p (insn, counts)
     rtx insn;
     int *counts;
{
  int i;
  if (flag_non_call_exceptions && may_trap_p (PATTERN (insn)))
    return true;
  else if (GET_CODE (PATTERN (insn)) == SET)
    return set_live_p (PATTERN (insn), insn, counts);
  else if (GET_CODE (PATTERN (insn)) == PARALLEL)
    {
      for (i = XVECLEN (PATTERN (insn), 0) - 1; i >= 0; i--)
	{
	  rtx elt = XVECEXP (PATTERN (insn), 0, i);

	  if (GET_CODE (elt) == SET)
	    {
	      if (set_live_p (elt, insn, counts))
		return true;
	    }
	  else if (GET_CODE (elt) != CLOBBER && GET_CODE (elt) != USE)
	    return true;
	}
      return false;
    }
  else
    return true;
}

/* Return true if libcall is dead as a whole.  */

static bool
dead_libcall_p (insn, counts)
     rtx insn;
     int *counts;
{
  rtx note;
  /* See if there's a REG_EQUAL note on this insn and try to
     replace the source with the REG_EQUAL expression.

     We assume that insns with REG_RETVALs can only be reg->reg
     copies at this point.  */
  note = find_reg_note (insn, REG_EQUAL, NULL_RTX);
  if (note)
    {
      rtx set = single_set (insn);
      rtx new = simplify_rtx (XEXP (note, 0));

      if (!new)
	new = XEXP (note, 0);

      /* While changing insn, we must update the counts accordingly.  */
      count_reg_usage (insn, counts, NULL_RTX, -1);

      if (set && validate_change (insn, &SET_SRC (set), new, 0))
	{
          count_reg_usage (insn, counts, NULL_RTX, 1);
	  remove_note (insn, find_reg_note (insn, REG_RETVAL, NULL_RTX));
	  remove_note (insn, note);
	  return true;
	}
       count_reg_usage (insn, counts, NULL_RTX, 1);
    }
  return false;
}

/* Scan all the insns and delete any that are dead; i.e., they store a register
   that is never used or they copy a register to itself.

   This is used to remove insns made obviously dead by cse, loop or other
   optimizations.  It improves the heuristics in loop since it won't try to
   move dead invariants out of loops or make givs for dead quantities.  The
   remaining passes of the compilation are also sped up.  */

int
delete_trivially_dead_insns (insns, nreg)
     rtx insns;
     int nreg;
{
  int *counts;
  rtx insn, prev;
  int in_libcall = 0, dead_libcall = 0;
  int ndead = 0, nlastdead, niterations = 0;

  timevar_push (TV_DELETE_TRIVIALLY_DEAD);
  /* First count the number of times each register is used.  */
  counts = (int *) xcalloc (nreg, sizeof (int));
  for (insn = next_real_insn (insns); insn; insn = next_real_insn (insn))
    count_reg_usage (insn, counts, NULL_RTX, 1);

  do
    {
      nlastdead = ndead;
      niterations++;
      /* Go from the last insn to the first and delete insns that only set unused
	 registers or copy a register to itself.  As we delete an insn, remove
	 usage counts for registers it uses.

	 The first jump optimization pass may leave a real insn as the last
	 insn in the function.   We must not skip that insn or we may end
	 up deleting code that is not really dead.  */
      insn = get_last_insn ();
      if (! INSN_P (insn))
	insn = prev_real_insn (insn);

      for (; insn; insn = prev)
	{
	  int live_insn = 0;

	  prev = prev_real_insn (insn);

	  /* Don't delete any insns that are part of a libcall block unless
	     we can delete the whole libcall block.

	     Flow or loop might get confused if we did that.  Remember
	     that we are scanning backwards.  */
	  if (find_reg_note (insn, REG_RETVAL, NULL_RTX))
	    {
	      in_libcall = 1;
	      live_insn = 1;
	      dead_libcall = dead_libcall_p (insn, counts);
	    }
	  else if (in_libcall)
	    live_insn = ! dead_libcall;
	  else
	    live_insn = insn_live_p (insn, counts);

	  /* If this is a dead insn, delete it and show registers in it aren't
	     being used.  */

	  if (! live_insn)
	    {
	      count_reg_usage (insn, counts, NULL_RTX, -1);
	      delete_insn_and_edges (insn);
	      ndead++;
	    }

	  if (find_reg_note (insn, REG_LIBCALL, NULL_RTX))
	    {
	      in_libcall = 0;
	      dead_libcall = 0;
	    }
	}
    }
  while (ndead != nlastdead);

  if (rtl_dump_file && ndead)
    fprintf (rtl_dump_file, "Deleted %i trivially dead insns; %i iterations\n",
	     ndead, niterations);
  /* Clean up.  */
  free (counts);
  timevar_pop (TV_DELETE_TRIVIALLY_DEAD);
  return ndead;
}

/* This function is called via for_each_rtx.  The argument, NEWREG, is
   a condition code register with the desired mode.  If we are looking
   at the same register in a different mode, replace it with
   NEWREG.  */

static int
cse_change_cc_mode (loc, data)
     rtx *loc;
     void *data;
{
  rtx newreg = (rtx) data;

  if (*loc
      && GET_CODE (*loc) == REG
      && REGNO (*loc) == REGNO (newreg)
      && GET_MODE (*loc) != GET_MODE (newreg))
    {
      *loc = newreg;
      return -1;
    }
  return 0;
}

/* Change the mode of any reference to the register REGNO (NEWREG) to
   GET_MODE (NEWREG), starting at START.  Stop before END.  Stop at
   any instruction which modifies NEWREG.  */

static void
cse_change_cc_mode_insns (start, end, newreg)
     rtx start;
     rtx end;
     rtx newreg;
{
  rtx insn;

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

      if (reg_set_p (newreg, insn))
	return;

      for_each_rtx (&PATTERN (insn), cse_change_cc_mode, newreg);
      for_each_rtx (&REG_NOTES (insn), cse_change_cc_mode, newreg);
    }
}

/* BB is a basic block which finishes with CC_REG as a condition code
   register which is set to CC_SRC.  Look through the successors of BB
   to find blocks which have a single predecessor (i.e., this one),
   and look through those blocks for an assignment to CC_REG which is
   equivalent to CC_SRC.  CAN_CHANGE_MODE indicates whether we are
   permitted to change the mode of CC_SRC to a compatible mode.  This
   returns VOIDmode if no equivalent assignments were found.
   Otherwise it returns the mode which CC_SRC should wind up with.

   The main complexity in this function is handling the mode issues.
   We may have more than one duplicate which we can eliminate, and we
   try to find a mode which will work for multiple duplicates.  */

static enum machine_mode
cse_cc_succs (bb, cc_reg, cc_src, can_change_mode)
     basic_block bb;
     rtx cc_reg;
     rtx cc_src;
     int can_change_mode;
{
  bool found_equiv;
  enum machine_mode mode;
  unsigned int insn_count;
  edge e;
  rtx insns[2];
  enum machine_mode modes[2];
  rtx last_insns[2];
  unsigned int i;
  rtx newreg;

  /* We expect to have two successors.  Look at both before picking
     the final mode for the comparison.  If we have more successors
     (i.e., some sort of table jump, although that seems unlikely),
     then we require all beyond the first two to use the same
     mode.  */

  found_equiv = false;
  mode = GET_MODE (cc_src);
  insn_count = 0;
  for (e = bb->succ; e; e = e->succ_next)
    {
      rtx insn;
      rtx end;

      if (e->flags & EDGE_COMPLEX)
	continue;

      if (! e->dest->pred
	  || e->dest->pred->pred_next
	  || e->dest == EXIT_BLOCK_PTR)
	continue;

      end = NEXT_INSN (e->dest->end);
      for (insn = e->dest->head; insn != end; insn = NEXT_INSN (insn))
	{
	  rtx set;

	  if (! INSN_P (insn))
	    continue;

	  /* If CC_SRC is modified, we have to stop looking for
	     something which uses it.  */
	  if (modified_in_p (cc_src, insn))
	    break;

	  /* Check whether INSN sets CC_REG to CC_SRC.  */
	  set = single_set (insn);
	  if (set
	      && GET_CODE (SET_DEST (set)) == REG
	      && REGNO (SET_DEST (set)) == REGNO (cc_reg))
	    {
	      bool found;
	      enum machine_mode set_mode;
	      enum machine_mode comp_mode;

	      found = false;
	      set_mode = GET_MODE (SET_SRC (set));
	      comp_mode = set_mode;
	      if (rtx_equal_p (cc_src, SET_SRC (set)))
		found = true;
	      else if (GET_CODE (cc_src) == COMPARE
		       && GET_CODE (SET_SRC (set)) == COMPARE
		       && mode != set_mode
		       && rtx_equal_p (XEXP (cc_src, 0),
				       XEXP (SET_SRC (set), 0))
		       && rtx_equal_p (XEXP (cc_src, 1),
				       XEXP (SET_SRC (set), 1)))
			   
		{
		  comp_mode = (*targetm.cc_modes_compatible) (mode, set_mode);
		  if (comp_mode != VOIDmode
		      && (can_change_mode || comp_mode == mode))
		    found = true;
		}

	      if (found)
		{
		  found_equiv = true;
		  if (insn_count < ARRAY_SIZE (insns))
		    {
		      insns[insn_count] = insn;
		      modes[insn_count] = set_mode;
		      last_insns[insn_count] = end;
		      ++insn_count;

		      if (mode != comp_mode)
			{
			  if (! can_change_mode)
			    abort ();
			  mode = comp_mode;
			  PUT_MODE (cc_src, mode);
			}
		    }
		  else
		    {
		      if (set_mode != mode)
			{
			  /* We found a matching expression in the
			     wrong mode, but we don't have room to
			     store it in the array.  Punt.  This case
			     should be rare.  */
			  break;
			}
		      /* INSN sets CC_REG to a value equal to CC_SRC
			 with the right mode.  We can simply delete
			 it.  */
		      delete_insn (insn);
		    }

		  /* We found an instruction to delete.  Keep looking,
		     in the hopes of finding a three-way jump.  */
		  continue;
		}

	      /* We found an instruction which sets the condition
		 code, so don't look any farther.  */
	      break;
	    }

	  /* If INSN sets CC_REG in some other way, don't look any
	     farther.  */
	  if (reg_set_p (cc_reg, insn))
	    break;
	}

      /* If we fell off the bottom of the block, we can keep looking
	 through successors.  We pass CAN_CHANGE_MODE as false because
	 we aren't prepared to handle compatibility between the
	 further blocks and this block.  */
      if (insn == end)
	{
	  enum machine_mode submode;

	  submode = cse_cc_succs (e->dest, cc_reg, cc_src, false);
	  if (submode != VOIDmode)
	    {
	      if (submode != mode)
		abort ();
	      found_equiv = true;
	      can_change_mode = false;
	    }
	}
    }

  if (! found_equiv)
    return VOIDmode;

  /* Now INSN_COUNT is the number of instructions we found which set
     CC_REG to a value equivalent to CC_SRC.  The instructions are in
     INSNS.  The modes used by those instructions are in MODES.  */

  newreg = NULL_RTX;
  for (i = 0; i < insn_count; ++i)
    {
      if (modes[i] != mode)
	{
	  /* We need to change the mode of CC_REG in INSNS[i] and
	     subsequent instructions.  */
	  if (! newreg)
	    {
	      if (GET_MODE (cc_reg) == mode)
		newreg = cc_reg;
	      else
		newreg = gen_rtx_REG (mode, REGNO (cc_reg));
	    }
	  cse_change_cc_mode_insns (NEXT_INSN (insns[i]), last_insns[i],
				    newreg);
	}

      delete_insn (insns[i]);
    }

  return mode;
}

/* If we have a fixed condition code register (or two), walk through
   the instructions and try to eliminate duplicate assignments.  */

void
cse_condition_code_reg ()
{
  unsigned int cc_regno_1;
  unsigned int cc_regno_2;
  rtx cc_reg_1;
  rtx cc_reg_2;
  basic_block bb;

  if (! (*targetm.fixed_condition_code_regs) (&cc_regno_1, &cc_regno_2))
    return;

  cc_reg_1 = gen_rtx_REG (CCmode, cc_regno_1);
  if (cc_regno_2 != INVALID_REGNUM)
    cc_reg_2 = gen_rtx_REG (CCmode, cc_regno_2);
  else
    cc_reg_2 = NULL_RTX;

  FOR_EACH_BB (bb)
    {
      rtx last_insn;
      rtx cc_reg;
      rtx insn;
      rtx cc_src_insn;
      rtx cc_src;
      enum machine_mode mode;
      enum machine_mode orig_mode;

      /* Look for blocks which end with a conditional jump based on a
	 condition code register.  Then look for the instruction which
	 sets the condition code register.  Then look through the
	 successor blocks for instructions which set the condition
	 code register to the same value.  There are other possible
	 uses of the condition code register, but these are by far the
	 most common and the ones which we are most likely to be able
	 to optimize.  */

      last_insn = bb->end;
      if (GET_CODE (last_insn) != JUMP_INSN)
	continue;

      if (reg_referenced_p (cc_reg_1, PATTERN (last_insn)))
	cc_reg = cc_reg_1;
      else if (cc_reg_2 && reg_referenced_p (cc_reg_2, PATTERN (last_insn)))
	cc_reg = cc_reg_2;
      else
	continue;

      cc_src_insn = NULL_RTX;
      cc_src = NULL_RTX;
      for (insn = PREV_INSN (last_insn);
	   insn && insn != PREV_INSN (bb->head);
	   insn = PREV_INSN (insn))
	{
	  rtx set;

	  if (! INSN_P (insn))
	    continue;
	  set = single_set (insn);
	  if (set
	      && GET_CODE (SET_DEST (set)) == REG
	      && REGNO (SET_DEST (set)) == REGNO (cc_reg))
	    {
	      cc_src_insn = insn;
	      cc_src = SET_SRC (set);
	      break;
	    }
	  else if (reg_set_p (cc_reg, insn))
	    break;
	}

      if (! cc_src_insn)
	continue;

      if (modified_between_p (cc_src, cc_src_insn, NEXT_INSN (last_insn)))
	continue;

      /* Now CC_REG is a condition code register used for a
	 conditional jump at the end of the block, and CC_SRC, in
	 CC_SRC_INSN, is the value to which that condition code
	 register is set, and CC_SRC is still meaningful at the end of
	 the basic block.  */

      orig_mode = GET_MODE (cc_src);
      mode = cse_cc_succs (bb, cc_reg, cc_src, true);
      if (mode != VOIDmode)
	{
	  if (mode != GET_MODE (cc_src))
	    abort ();
	  if (mode != orig_mode)
	    {
	      rtx newreg = gen_rtx_REG (mode, REGNO (cc_reg));

	      /* Change the mode of CC_REG in CC_SRC_INSN to
		 GET_MODE (NEWREG).  */
	      for_each_rtx (&PATTERN (cc_src_insn), cse_change_cc_mode,
			    newreg);
	      for_each_rtx (&REG_NOTES (cc_src_insn), cse_change_cc_mode,
			    newreg);

	      /* Do the same in the following insns that use the
		 current value of CC_REG within BB.  */
	      cse_change_cc_mode_insns (NEXT_INSN (cc_src_insn),
					NEXT_INSN (last_insn),
					newreg);
	    }
	}
    }
}

enum machine_mode
default_cc_modes_compatible (m1, m2)
     enum machine_mode m1;
     enum machine_mode m2;
{
  if (m1 == m2)
    return m1;
  return VOIDmode;
}
