]> gcc.gnu.org Git - gcc.git/commitdiff
re PR rtl-optimization/57708 (function clobbers callee saved register on ARM)
authorRichard Earnshaw <rearnsha@arm.com>
Mon, 5 Aug 2013 17:58:22 +0000 (17:58 +0000)
committerRichard Earnshaw <rearnsha@gcc.gnu.org>
Mon, 5 Aug 2013 17:58:22 +0000 (17:58 +0000)
PR rtl-optimization/57708
* recog.c (peep2_find_free_register): Validate all regs in a
multi-reg mode.

From-SVN: r201501

gcc/ChangeLog
gcc/recog.c

index a40d4a0afbf8140c4a4108b648a97cc2a05cfe43..eece522af1a229e6da0f7308cd41764a36897884 100644 (file)
@@ -1,3 +1,9 @@
+2013-08-05  Richard Earnshaw  <rearnsha@arm.com>
+
+       PR rtl-optimization/57708
+       * recog.c (peep2_find_free_register): Validate all regs in a
+       multi-reg mode.
+
 2013-08-05  Jan Hubicka  <jh@suse.cz>
 
        PR lto/57602
index 6a607ba2a5aff6671f0afcdaba74b68ce987989d..aa026a27d59938e8d64098b0998be64ecd6e9b48 100644 (file)
@@ -3124,32 +3124,53 @@ peep2_find_free_register (int from, int to, const char *class_str,
       regno = raw_regno;
 #endif
 
-      /* Don't allocate fixed registers.  */
-      if (fixed_regs[regno])
-       continue;
-      /* Don't allocate global registers.  */
-      if (global_regs[regno])
-       continue;
-      /* Make sure the register is of the right class.  */
-      if (! TEST_HARD_REG_BIT (reg_class_contents[cl], regno))
-       continue;
-      /* And can support the mode we need.  */
+      /* Can it support the mode we need?  */
       if (! HARD_REGNO_MODE_OK (regno, mode))
        continue;
-      /* And that we don't create an extra save/restore.  */
-      if (! call_used_regs[regno] && ! df_regs_ever_live_p (regno))
-       continue;
-      if (! targetm.hard_regno_scratch_ok (regno))
-       continue;
-
-      /* And we don't clobber traceback for noreturn functions.  */
-      if ((regno == FRAME_POINTER_REGNUM || regno == HARD_FRAME_POINTER_REGNUM)
-         && (! reload_completed || frame_pointer_needed))
-       continue;
 
       success = 1;
-      for (j = hard_regno_nregs[regno][mode] - 1; j >= 0; j--)
+      for (j = 0; success && j < hard_regno_nregs[regno][mode]; j++)
        {
+         /* Don't allocate fixed registers.  */
+         if (fixed_regs[regno + j])
+           {
+             success = 0;
+             break;
+           }
+         /* Don't allocate global registers.  */
+         if (global_regs[regno + j])
+           {
+             success = 0;
+             break;
+           }
+         /* Make sure the register is of the right class.  */
+         if (! TEST_HARD_REG_BIT (reg_class_contents[cl], regno + j))
+           {
+             success = 0;
+             break;
+           }
+         /* And that we don't create an extra save/restore.  */
+         if (! call_used_regs[regno + j] && ! df_regs_ever_live_p (regno + j))
+           {
+             success = 0;
+             break;
+           }
+
+         if (! targetm.hard_regno_scratch_ok (regno + j))
+           {
+             success = 0;
+             break;
+           }
+
+         /* And we don't clobber traceback for noreturn functions.  */
+         if ((regno + j == FRAME_POINTER_REGNUM
+              || regno + j == HARD_FRAME_POINTER_REGNUM)
+             && (! reload_completed || frame_pointer_needed))
+           {
+             success = 0;
+             break;
+           }
+
          if (TEST_HARD_REG_BIT (*reg_set, regno + j)
              || TEST_HARD_REG_BIT (live, regno + j))
            {
@@ -3157,6 +3178,7 @@ peep2_find_free_register (int from, int to, const char *class_str,
              break;
            }
        }
+
       if (success)
        {
          add_to_hard_reg_set (reg_set, mode, regno);
This page took 0.104187 seconds and 5 git commands to generate.