IA MCU psABI support: changes to libraries
[gcc.git] / gcc / lra-constraints.c
index 827c453b0fb111c866f79386f6f8b98ad00275e6..1d3f94e5ab07a693bfe932301e81a406e8426bf3 100644 (file)
 #include "output.h"
 #include "addresses.h"
 #include "target.h"
-#include "hashtab.h"
-#include "hash-set.h"
-#include "vec.h"
-#include "machmode.h"
-#include "input.h"
 #include "function.h"
 #include "symtab.h"
 #include "flags.h"
-#include "statistics.h"
-#include "double-int.h"
-#include "real.h"
-#include "fixed-value.h"
 #include "alias.h"
-#include "wide-int.h"
-#include "inchash.h"
 #include "tree.h"
 #include "expmed.h"
 #include "dojump.h"
 #include "df.h"
 #include "ira.h"
 #include "rtl-error.h"
+#include "params.h"
 #include "lra-int.h"
 
 /* Value of LRA_CURR_RELOAD_NUM at the beginning of BB of the current
@@ -532,7 +522,7 @@ get_equiv_with_elimination (rtx x, rtx_insn *insn)
   if (x == res || CONSTANT_P (res))
     return res;
   return lra_eliminate_regs_1 (insn, res, GET_MODE (res),
-                              0, false, false, true);
+                              false, false, 0, true);
 }
 
 /* Set up curr_operand_mode.  */
@@ -748,6 +738,9 @@ operands_match_p (rtx x, rtx y, int y_hard_regno)
 
  slow:
 
+  if (code == REG && REG_P (y))
+    return REGNO (x) == REGNO (y);
+
   if (code == REG && GET_CODE (y) == SUBREG && REG_P (SUBREG_REG (y))
       && x == SUBREG_REG (y))
     return true;
@@ -872,7 +865,7 @@ match_reload (signed char out, signed char *ins, enum reg_class goal_class,
              rtx_insn **before, rtx_insn **after)
 {
   int i, in;
-  rtx new_in_reg, new_out_reg, reg, clobber;
+  rtx new_in_reg, new_out_reg, reg;
   machine_mode inmode, outmode;
   rtx in_rtx = *curr_id->operand_loc[ins[0]];
   rtx out_rtx = out < 0 ? in_rtx : *curr_id->operand_loc[out];
@@ -913,7 +906,7 @@ match_reload (signed char out, signed char *ins, enum reg_class goal_class,
             NEW_OUT_REG living above.  We add clobber clause for
             this.  This is just a temporary clobber.  We can remove
             it at the end of LRA work.  */
-         clobber = emit_clobber (new_out_reg);
+         rtx_insn *clobber = emit_clobber (new_out_reg);
          LRA_TEMP_CLOBBER_P (PATTERN (clobber)) = 1;
          LRA_SUBREG_P (new_in_reg) = 1;
          if (GET_CODE (in_rtx) == SUBREG)
@@ -1059,9 +1052,8 @@ emit_spill_move (bool to_p, rtx mem_pseudo, rtx val)
          LRA_SUBREG_P (mem_pseudo) = 1;
        }
     }
-  return as_a <rtx_insn *> (to_p
-                           ? gen_move_insn (mem_pseudo, val)
-                           : gen_move_insn (val, mem_pseudo));
+  return to_p ? gen_move_insn (mem_pseudo, val)
+             : gen_move_insn (val, mem_pseudo);
 }
 
 /* Process a special case insn (register move), return true if we
@@ -1073,10 +1065,9 @@ static bool
 check_and_process_move (bool *change_p, bool *sec_mem_p ATTRIBUTE_UNUSED)
 {
   int sregno, dregno;
-  rtx dest, src, dreg, sreg, old_sreg, new_reg, scratch_reg;
+  rtx dest, src, dreg, sreg, new_reg, scratch_reg;
   rtx_insn *before;
   enum reg_class dclass, sclass, secondary_class;
-  machine_mode sreg_mode;
   secondary_reload_info sri;
 
   lra_assert (curr_insn_set != NULL_RTX);
@@ -1100,8 +1091,6 @@ check_and_process_move (bool *change_p, bool *sec_mem_p ATTRIBUTE_UNUSED)
        were a right class for the pseudo, secondary_... hooks usually
        are not define for ALL_REGS.  */
     return false;
-  sreg_mode = GET_MODE (sreg);
-  old_sreg = sreg;
   if (REG_P (sreg))
     sclass = get_reg_class (REGNO (sreg));
   if (sclass == ALL_REGS)
@@ -1160,9 +1149,9 @@ check_and_process_move (bool *change_p, bool *sec_mem_p ATTRIBUTE_UNUSED)
       sri.icode = CODE_FOR_nothing;
       sri.extra_cost = 0;
       secondary_class
-       = (enum reg_class) targetm.secondary_reload (true, sreg,
+       = (enum reg_class) targetm.secondary_reload (true, src,
                                                     (reg_class_t) dclass,
-                                                    sreg_mode, &sri);
+                                                    GET_MODE (src), &sri);
       /* Check the target hook consistency.  */
       lra_assert
        ((secondary_class == NO_REGS && sri.icode == CODE_FOR_nothing)
@@ -1178,14 +1167,12 @@ check_and_process_move (bool *change_p, bool *sec_mem_p ATTRIBUTE_UNUSED)
   *change_p = true;
   new_reg = NULL_RTX;
   if (secondary_class != NO_REGS)
-    new_reg = lra_create_new_reg_with_unique_value (sreg_mode, NULL_RTX,
+    new_reg = lra_create_new_reg_with_unique_value (GET_MODE (src), NULL_RTX,
                                                    secondary_class,
                                                    "secondary");
   start_sequence ();
-  if (old_sreg != sreg)
-    sreg = copy_rtx (sreg);
   if (sri.icode == CODE_FOR_nothing)
-    lra_emit_move (new_reg, sreg);
+    lra_emit_move (new_reg, src);
   else
     {
       enum reg_class scratch_class;
@@ -1196,18 +1183,13 @@ check_and_process_move (bool *change_p, bool *sec_mem_p ATTRIBUTE_UNUSED)
                     (insn_data[sri.icode].operand[2].mode, NULL_RTX,
                      scratch_class, "scratch"));
       emit_insn (GEN_FCN (sri.icode) (new_reg != NULL_RTX ? new_reg : dest,
-                                     sreg, scratch_reg));
+                                     src, scratch_reg));
     }
   before = get_insns ();
   end_sequence ();
   lra_process_new_insns (curr_insn, before, NULL, "Inserting the move");
   if (new_reg != NULL_RTX)
-    {
-      if (GET_CODE (src) == SUBREG)
-       SUBREG_REG (src) = new_reg;
-      else
-       SET_SRC (curr_insn_set) = new_reg;
-    }
+    SET_SRC (curr_insn_set) = new_reg;
   else
     {
       if (lra_dump_file != NULL)
@@ -1665,7 +1647,7 @@ prohibited_class_reg_set_mode_p (enum reg_class rclass,
 {
   HARD_REG_SET temp;
   
-  lra_assert (hard_reg_set_subset_p (set, reg_class_contents[rclass]));
+  lra_assert (hard_reg_set_subset_p (reg_class_contents[rclass], set));
   COPY_HARD_REG_SET (temp, set);
   AND_COMPL_HARD_REG_SET (temp, lra_no_alloc_regs);
   return (hard_reg_set_subset_p
@@ -2697,7 +2679,7 @@ base_to_reg (struct address_info *ad)
                                    : *ad->disp_term);
   if (!valid_address_p (ad->mode, new_inner, ad->as))
     return NULL_RTX;
-  insn = emit_insn (gen_rtx_SET (ad->mode, new_reg, *ad->base_term));
+  insn = emit_insn (gen_rtx_SET (new_reg, *ad->base_term));
   code = recog_memoized (insn);
   if (code < 0)
     {
@@ -2969,42 +2951,42 @@ process_address_1 (int nop, bool check_only_p,
          rtx addr = *ad.inner;
 
          new_reg = lra_create_new_reg (Pmode, NULL_RTX, cl, "addr");
-#ifdef HAVE_lo_sum
-         {
-           rtx_insn *insn;
-           rtx_insn *last = get_last_insn ();
-
-           /* addr => lo_sum (new_base, addr), case (2) above.  */
-           insn = emit_insn (gen_rtx_SET
-                             (VOIDmode, new_reg,
-                              gen_rtx_HIGH (Pmode, copy_rtx (addr))));
-           code = recog_memoized (insn);
-           if (code >= 0)
-             {
-               *ad.inner = gen_rtx_LO_SUM (Pmode, new_reg, addr);
-               if (! valid_address_p (ad.mode, *ad.outer, ad.as))
-                 {
-                   /* Try to put lo_sum into register.  */
-                   insn = emit_insn (gen_rtx_SET
-                                     (VOIDmode, new_reg,
-                                      gen_rtx_LO_SUM (Pmode, new_reg, addr)));
-                   code = recog_memoized (insn);
-                   if (code >= 0)
-                     {
-                       *ad.inner = new_reg;
-                       if (! valid_address_p (ad.mode, *ad.outer, ad.as))
-                         {
-                           *ad.inner = addr;
-                           code = -1;
-                         }
-                     }
-                   
-                 }
-             }
-           if (code < 0)
-             delete_insns_since (last);
-         }
-#endif
+         if (HAVE_lo_sum)
+           {
+             rtx_insn *insn;
+             rtx_insn *last = get_last_insn ();
+
+             /* addr => lo_sum (new_base, addr), case (2) above.  */
+             insn = emit_insn (gen_rtx_SET
+                               (new_reg,
+                                gen_rtx_HIGH (Pmode, copy_rtx (addr))));
+             code = recog_memoized (insn);
+             if (code >= 0)
+               {
+                 *ad.inner = gen_rtx_LO_SUM (Pmode, new_reg, addr);
+                 if (! valid_address_p (ad.mode, *ad.outer, ad.as))
+                   {
+                     /* Try to put lo_sum into register.  */
+                     insn = emit_insn (gen_rtx_SET
+                                       (new_reg,
+                                        gen_rtx_LO_SUM (Pmode, new_reg, addr)));
+                     code = recog_memoized (insn);
+                     if (code >= 0)
+                       {
+                         *ad.inner = new_reg;
+                         if (! valid_address_p (ad.mode, *ad.outer, ad.as))
+                           {
+                             *ad.inner = addr;
+                             code = -1;
+                           }
+                       }
+
+                   }
+               }
+             if (code < 0)
+               delete_insns_since (last);
+           }
+
          if (code < 0)
            {
              /* addr => new_base, case (2) above.  */
@@ -3302,15 +3284,9 @@ simple_move_p (void)
 static inline void
 swap_operands (int nop)
 {
-  machine_mode mode = curr_operand_mode[nop];
-  curr_operand_mode[nop] = curr_operand_mode[nop + 1];
-  curr_operand_mode[nop + 1] = mode;
-  mode = original_subreg_reg_mode[nop];
-  original_subreg_reg_mode[nop] = original_subreg_reg_mode[nop + 1];
-  original_subreg_reg_mode[nop + 1] = mode;
-  rtx x = *curr_id->operand_loc[nop];
-  *curr_id->operand_loc[nop] = *curr_id->operand_loc[nop + 1];
-  *curr_id->operand_loc[nop + 1] = x;
+  std::swap (curr_operand_mode[nop], curr_operand_mode[nop + 1]);
+  std::swap (original_subreg_reg_mode[nop], original_subreg_reg_mode[nop + 1]);
+  std::swap (*curr_id->operand_loc[nop], *curr_id->operand_loc[nop + 1]);
   /* Swap the duplicates too.  */
   lra_update_dup (curr_id, nop);
   lra_update_dup (curr_id, nop + 1);
@@ -3363,12 +3339,10 @@ curr_insn_transform (bool check_only_p)
   if (JUMP_P (curr_insn) || CALL_P (curr_insn))
     no_output_reloads_p = true;
 
-#ifdef HAVE_cc0
-  if (reg_referenced_p (cc0_rtx, PATTERN (curr_insn)))
+  if (HAVE_cc0 && reg_referenced_p (cc0_rtx, PATTERN (curr_insn)))
     no_input_reloads_p = true;
-  if (reg_set_p (cc0_rtx, PATTERN (curr_insn)))
+  if (HAVE_cc0 && reg_set_p (cc0_rtx, PATTERN (curr_insn)))
     no_output_reloads_p = true;
-#endif
 
   n_operands = curr_static_id->n_operands;
   n_alternatives = curr_static_id->n_alternatives;
@@ -4152,7 +4126,7 @@ contains_deleted_insn_p (rtx_insn_list *list)
 
 /* Return true if X contains a pseudo dying in INSN.  */
 static bool
-dead_pseudo_p (rtx x, rtx insn)
+dead_pseudo_p (rtx x, rtx_insn *insn)
 {
   int i, j;
   const char *fmt;
@@ -4777,7 +4751,7 @@ inherit_reload_reg (bool def_p, int original_regno,
                   "    Inheritance reuse change %d->%d (bb%d):\n",
                   original_regno, REGNO (new_reg),
                   BLOCK_FOR_INSN (usage_insn)->index);
-         dump_insn_slim (lra_dump_file, usage_insn);
+         dump_insn_slim (lra_dump_file, as_a <rtx_insn *> (usage_insn));
        }
     }
   if (lra_dump_file != NULL)
@@ -5037,7 +5011,7 @@ split_reg (bool before_p, int original_regno, rtx_insn *insn,
        {
          fprintf (lra_dump_file, "    Split reuse change %d->%d:\n",
                   original_regno, REGNO (new_reg));
-         dump_insn_slim (lra_dump_file, usage_insn);
+         dump_insn_slim (lra_dump_file, as_a <rtx_insn *> (usage_insn));
        }
     }
   lra_assert (NOTE_P (usage_insn) || NONDEBUG_INSN_P (usage_insn));
@@ -5578,7 +5552,7 @@ inherit_in_ebb (rtx_insn *head, rtx_insn *tail)
                           || reg_renumber[src_regno] >= 0)
                    {
                      bool before_p;
-                     rtx use_insn = curr_insn;
+                     rtx_insn *use_insn = curr_insn;
 
                      before_p = (JUMP_P (curr_insn)
                                  || (CALL_P (curr_insn) && reg->type == OP_IN));
@@ -5694,7 +5668,8 @@ inherit_in_ebb (rtx_insn *head, rtx_insn *tail)
 /* This value affects EBB forming.  If probability of edge from EBB to
    a BB is not greater than the following value, we don't add the BB
    to EBB.  */
-#define EBB_PROBABILITY_CUTOFF ((REG_BR_PROB_BASE * 50) / 100)
+#define EBB_PROBABILITY_CUTOFF \
+  ((REG_BR_PROB_BASE * LRA_INHERITANCE_EBB_PROBABILITY_CUTOFF) / 100)
 
 /* Current number of inheritance/split iteration.  */
 int lra_inheritance_iter;
@@ -5740,7 +5715,7 @@ lra_inheritance (void)
          e = find_fallthru_edge (bb->succs);
          if (! e)
            break;
-         if (e->probability <= EBB_PROBABILITY_CUTOFF)
+         if (e->probability < EBB_PROBABILITY_CUTOFF)
            break;
          bb = bb->next_bb;
        }