]> gcc.gnu.org Git - gcc.git/commitdiff
re PR rtl-optimization/55106 (ice: Maximum number of LRA constraint passes is achieve...
authorVladimir Makarov <vmakarov@redhat.com>
Mon, 29 Oct 2012 00:42:25 +0000 (00:42 +0000)
committerVladimir Makarov <vmakarov@gcc.gnu.org>
Mon, 29 Oct 2012 00:42:25 +0000 (00:42 +0000)
2012-10-28  Vladimir Makarov  <vmakarov@redhat.com>

PR rtl-optimization/55106
* lra-constraints.c (skip_usage_debug_insns): New function.
(check_secondary_memory_needed_p): Ditto.
(inherit_reload_reg): Use the new functions.  Improve debug
output.

From-SVN: r192904

gcc/ChangeLog
gcc/lra-constraints.c

index e1235d2df0c7eb19aabfe70b243fab69d5b95e5b..107d6f6f651a50e870b0aeb1c8ce6e9cc0804ee9 100644 (file)
@@ -1,3 +1,11 @@
+2012-10-28  Vladimir Makarov  <vmakarov@redhat.com>
+
+       PR rtl-optimization/55106
+       * lra-constraints.c (skip_usage_debug_insns): New function.
+       (check_secondary_memory_needed_p): Ditto.
+       (inherit_reload_reg): Use the new functions.  Improve debug
+       output.
+
 2012-10-29  Jonathan Wakely  <jwakely.gcc@gmail.com>
 
        * doc/cpp.texi (Search Path): Fix outdated C++ path.
index 4b3dbc01ec30e4646e96ec04a30cb0662bbee2d7..c9a8cd48330a4c3a517cfbd0008394adb10548b5 100644 (file)
@@ -3573,6 +3573,48 @@ substitute_pseudo (rtx *loc, int old_regno, rtx new_reg)
   return result;
 }
 
+/* Return first non-debug insn in list USAGE_INSNS.  */
+static rtx
+skip_usage_debug_insns (rtx usage_insns)
+{
+  rtx insn;
+
+  /* Skip debug insns.  */
+  for (insn = usage_insns;
+       insn != NULL_RTX && GET_CODE (insn) == INSN_LIST;
+       insn = XEXP (insn, 1))
+    ;
+  return insn;
+}
+
+/* Return true if we need secondary memory moves for insn in
+   USAGE_INSNS after inserting inherited pseudo of class INHER_CL
+   into the insn.  */
+static bool
+check_secondary_memory_needed_p (enum reg_class inher_cl, rtx usage_insns)
+{
+#ifndef SECONDARY_MEMORY_NEEDED
+  return false;
+#else
+  rtx insn, set, dest;
+  enum reg_class cl;
+
+  if (inher_cl == ALL_REGS
+      || (insn = skip_usage_debug_insns (usage_insns)) == NULL_RTX)
+    return false;
+  lra_assert (INSN_P (insn));
+  if ((set = single_set (insn)) == NULL_RTX || ! REG_P (SET_DEST (set)))
+    return false;
+  dest = SET_DEST (set);
+  if (! REG_P (dest))
+    return false;
+  lra_assert (inher_cl != NO_REGS);
+  cl = get_reg_class (REGNO (dest));
+  return (cl != NO_REGS && cl != ALL_REGS
+         && SECONDARY_MEMORY_NEEDED (inher_cl, cl, GET_MODE (dest)));
+#endif
+}
+
 /* Registers involved in inheritance/split in the current EBB
    (inheritance/split pseudos and original registers). */
 static bitmap_head check_only_regs;
@@ -3610,18 +3652,18 @@ inherit_reload_reg (bool def_p, int original_regno,
   lra_assert (! usage_insns[original_regno].after_p);
   if (lra_dump_file != NULL)
     fprintf (lra_dump_file,
-            "    <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n");
+            "    <<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<\n");
   if (! ira_reg_classes_intersect_p[cl][rclass])
     {
       if (lra_dump_file != NULL)
        {
          fprintf (lra_dump_file,
-                  "    Rejecting inheritance for %d "
+                  "    Rejecting inheritance for %d "
                   "because of disjoint classes %s and %s\n",
                   original_regno, reg_class_names[cl],
                   reg_class_names[rclass]);
          fprintf (lra_dump_file,
-                  "    >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>\n");
+                  "    >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>\n");
        }
       return false;
     }
@@ -3638,6 +3680,31 @@ inherit_reload_reg (bool def_p, int original_regno,
       
       rclass = cl;
     }
+  if (check_secondary_memory_needed_p (cl, next_usage_insns))
+    {
+      /* Reject inheritance resulting in secondary memory moves.
+        Otherwise, there is a danger in LRA cycling.  Also such
+        transformation will be unprofitable.  */
+      if (lra_dump_file != NULL)
+       {
+         rtx insn = skip_usage_debug_insns (next_usage_insns);
+         rtx set = single_set (insn);
+
+         lra_assert (set != NULL_RTX);
+
+         rtx dest = SET_DEST (set);
+
+         lra_assert (REG_P (dest));
+         fprintf (lra_dump_file,
+                  "    Rejecting inheritance for insn %d(%s)<-%d(%s) "
+                  "as secondary mem is needed\n",
+                  REGNO (dest), reg_class_names[get_reg_class (REGNO (dest))],
+                  original_regno, reg_class_names[cl]);
+         fprintf (lra_dump_file,
+                  "    >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>\n");
+       }
+      return false;
+    }
   new_reg = lra_create_new_reg (GET_MODE (original_reg), original_reg,
                                rclass, "inheritance");
   start_sequence ();
@@ -3652,7 +3719,7 @@ inherit_reload_reg (bool def_p, int original_regno,
       if (lra_dump_file != NULL)
        {
          fprintf (lra_dump_file,
-                  "    Rejecting inheritance %d->%d "
+                  "    Rejecting inheritance %d->%d "
                   "as it results in 2 or more insns:\n",
                   original_regno, REGNO (new_reg));
          debug_rtl_slim (lra_dump_file, new_insns, NULL_RTX, -1, 0);
@@ -3667,7 +3734,7 @@ inherit_reload_reg (bool def_p, int original_regno,
     /* We now have a new usage insn for original regno.  */
     setup_next_usage_insn (original_regno, new_insns, reloads_num, false);
   if (lra_dump_file != NULL)
-    fprintf (lra_dump_file, "   Original reg change %d->%d (bb%d):\n",
+    fprintf (lra_dump_file, "    Original reg change %d->%d (bb%d):\n",
             original_regno, REGNO (new_reg), BLOCK_FOR_INSN (insn)->index);
   lra_reg_info[REGNO (new_reg)].restore_regno = original_regno;
   bitmap_set_bit (&check_only_regs, REGNO (new_reg));
This page took 0.107974 seconds and 5 git commands to generate.