rs6000.md (movsi_to_cr): Remove the USE.
authorGeoff Keating <geoffk@cygnus.com>
Sun, 1 Oct 2000 05:29:14 +0000 (05:29 +0000)
committerGeoffrey Keating <geoffk@gcc.gnu.org>
Sun, 1 Oct 2000 05:29:14 +0000 (05:29 +0000)
* config/rs6000/rs6000.md (movsi_to_cr): Remove the USE.  Calculate
the mask value from the individual SET operations.
(return_internal_si): Move the USE after the RETURN.
(return_internal_di): Likewise.
(return_and_restore_fpregs_si): Likewise.
(return_and_restore_fpregs_di): Likewise.
(return_eh_si): Likewise.
(return_eh_di): Likewise.
* config/rs6000/rs6000.c (mtcrf_operation): Don't look for,
or check, the USE.
(rs6000_emit_prologue): Don't emit the USE for movsi_to_cr.
Don't generate a PARALLEL around a single operation movsi_to_cr.
Generate the RETURN first in any PARALLELs.

* rtlanal.c (single_set_1): Use fatal_insn to display the
invalid insn.  Check for more cases when a USE or CLOBBER occurs
before a SET.
* Makefile.in: Update dependencies for rtlanal.o.

From-SVN: r36683

gcc/ChangeLog
gcc/Makefile.in
gcc/config/rs6000/rs6000.c
gcc/config/rs6000/rs6000.md
gcc/rtlanal.c

index 9570b2835c0a29cbba97d3e46d933ce543dfb41a..15e6d46ae9989463788a7dbc6370da25f83ea638 100644 (file)
@@ -1,3 +1,24 @@
+2000-09-30  Geoff Keating  <geoffk@cygnus.com>
+
+       * config/rs6000/rs6000.md (movsi_to_cr): Remove the USE.  Calculate
+       the mask value from the individual SET operations.
+       (return_internal_si): Move the USE after the RETURN.
+       (return_internal_di): Likewise.
+       (return_and_restore_fpregs_si): Likewise.
+       (return_and_restore_fpregs_di): Likewise.
+       (return_eh_si): Likewise.
+       (return_eh_di): Likewise.
+       * config/rs6000/rs6000.c (mtcrf_operation): Don't look for,
+       or check, the USE.
+       (rs6000_emit_prologue): Don't emit the USE for movsi_to_cr.
+       Don't generate a PARALLEL around a single operation movsi_to_cr.
+       Generate the RETURN first in any PARALLELs.
+
+       * rtlanal.c (single_set_1): Use fatal_insn to display the
+       invalid insn.  Check for more cases when a USE or CLOBBER occurs
+       before a SET.
+       * Makefile.in: Update dependencies for rtlanal.o.
+
 2000-09-30  Joseph S. Myers  <jsm28@cam.ac.uk>
 
        * i386.c: Move include of "config.h" to before that of <setjmp.h>.
index f5cd9dc7714fc0f02f6263ca2c50d861a04c6ab0..c1ecef078be1aa34449aea75f59289a6b531882c 100644 (file)
@@ -1253,7 +1253,7 @@ rtl.o : rtl.c $(CONFIG_H) system.h $(RTL_H) bitmap.h $(GGC_H) toplev.h
 
 print-rtl.o : print-rtl.c $(CONFIG_H) system.h $(RTL_H) hard-reg-set.h \
     $(BASIC_BLOCK_H)
-rtlanal.o : rtlanal.c $(CONFIG_H) system.h $(RTL_H)
+rtlanal.o : rtlanal.c $(CONFIG_H) system.h toplev.h $(RTL_H)
 errors.o : errors.c $(CONFIG_H) system.h errors.h
 
 varasm.o : varasm.c $(CONFIG_H) system.h $(TREE_H) $(RTL_H) flags.h \
index 803c2db896556ca16e96f11d9ccc516715568929..e0bacdd775787bc861a47c63ebdf3afa557cafae 100644 (file)
@@ -3006,25 +3006,22 @@ mtcrf_operation (op, mode)
 {
   int count = XVECLEN (op, 0);
   int i;
-  int bitmap = 0;
   rtx src_reg;
 
   /* Perform a quick check so we don't blow up below.  */
-  if (count < 2
-      || GET_CODE (XVECEXP (op, 0, 0)) != USE
-      || GET_CODE (XEXP (XVECEXP (op, 0, 0), 0)) != CONST_INT
-      || GET_CODE (XVECEXP (op, 0, 1)) != SET
-      || GET_CODE (SET_SRC (XVECEXP (op, 0, 1))) != UNSPEC
-      || XVECLEN (SET_SRC (XVECEXP (op, 0, 1)), 0) != 2)
+  if (count < 1
+      || GET_CODE (XVECEXP (op, 0, 0)) != SET
+      || GET_CODE (SET_SRC (XVECEXP (op, 0, 0))) != UNSPEC
+      || XVECLEN (SET_SRC (XVECEXP (op, 0, 0)), 0) != 2)
     return 0;
-  src_reg = XVECEXP (SET_SRC (XVECEXP (op, 0, 1)), 0, 0);
+  src_reg = XVECEXP (SET_SRC (XVECEXP (op, 0, 0)), 0, 0);
   
   if (GET_CODE (src_reg) != REG
       || GET_MODE (src_reg) != SImode
       || ! INT_REGNO_P (REGNO (src_reg)))
     return 0;
 
-  for (i = 1; i < count; i++)
+  for (i = 0; i < count; i++)
     {
       rtx exp = XVECEXP (op, 0, i);
       rtx unspec;
@@ -3037,7 +3034,6 @@ mtcrf_operation (op, mode)
        return 0;
       unspec = SET_SRC (exp);
       maskval = 1 << (MAX_CR_REGNO - REGNO (SET_DEST (exp)));
-      bitmap |= maskval;
       
       if (GET_CODE (unspec) != UNSPEC
          || XINT (unspec, 1) != 20
@@ -3047,7 +3043,7 @@ mtcrf_operation (op, mode)
          || INTVAL (XVECEXP (unspec, 0, 1)) != maskval)
        return 0;
     }
-  return INTVAL (XEXP (XVECEXP (op, 0, 0), 0)) == bitmap;
+  return 1;
 }
 
 /* Return 1 for an PARALLEL suitable for lmw. */
@@ -5974,38 +5970,39 @@ rs6000_emit_epilogue(sibcall)
   if (info->cr_save_p)
     {
       rtx r12_rtx = gen_rtx_REG (SImode, 12);
+      int count = 0;
       
       if (using_mfcr_multiple)
        {
-         rtvec p;
-         int mask = 0;
-         int count = 0;
-
          for (i = 0; i < 8; i++)
            if (regs_ever_live[CR0_REGNO+i] && ! call_used_regs[CR0_REGNO+i])
-             {
-               mask |= 1 << (7-i);
-               count++;
-             }
+             count++;
          if (count == 0)
-           abort();
+           abort ();
+       }
+
+      if (using_mfcr_multiple && count > 1)
+       {
+         rtvec p;
+         int ndx;
          
-         p = rtvec_alloc (count + 1);
+         p = rtvec_alloc (count);
 
-         RTVEC_ELT (p, 0) = gen_rtx_USE (VOIDmode, GEN_INT (mask));
-         count = 1;
+         ndx = 0;
          for (i = 0; i < 8; i++)
            if (regs_ever_live[CR0_REGNO+i] && ! call_used_regs[CR0_REGNO+i])
              {
                rtvec r = rtvec_alloc (2);
                RTVEC_ELT (r, 0) = r12_rtx;
                RTVEC_ELT (r, 1) = GEN_INT (1 << (7-i));
-               RTVEC_ELT (p, count) =
+               RTVEC_ELT (p, ndx) =
                  gen_rtx_SET (VOIDmode, gen_rtx_REG (CCmode, CR0_REGNO+i), 
                               gen_rtx_UNSPEC (CCmode, r, 20));
-               count++;
+               ndx++;
              }
          emit_insn (gen_rtx_PARALLEL (VOIDmode, p));
+         if (ndx != count)
+           abort ();
        }
       else
        for (i = 0; i < 8; i++)
@@ -6050,10 +6047,10 @@ rs6000_emit_epilogue(sibcall)
       else
        p = rtvec_alloc (2);
 
-      RTVEC_ELT (p, 0) = gen_rtx_USE (VOIDmode, 
+      RTVEC_ELT (p, 0) = gen_rtx_RETURN (VOIDmode);
+      RTVEC_ELT (p, 1) = gen_rtx_USE (VOIDmode, 
                                      gen_rtx_REG (Pmode, 
                                                   LINK_REGISTER_REGNUM));
-      RTVEC_ELT (p, 1) = gen_rtx_RETURN (VOIDmode);
 
       /* If we have to restore more than two FP registers, branch to the
         restore function.  It will return to our caller.  */
index 132fb3c1ef7329ea9e4dab8b154807944d0bb1e4..43e74683bcf8429d69a2970af35463c3fc857a61 100644 (file)
@@ -13295,13 +13295,20 @@ operands[2] = GEN_INT (INTVAL (operands[1]) >> 32);
 
 (define_insn "*movsi_to_cr"
  [(match_parallel 0 "mtcrf_operation"
-                  [(use (match_operand 1 "immediate_operand" "n"))
-                  (set (match_operand:CC 2 "cc_reg_operand" "=y")
-                               (unspec:CC [(match_operand:SI 3 "gpc_reg_operand" "r")
-                                   (match_operand 4 "immediate_operand" "n")]
+                  [(set (match_operand:CC 1 "cc_reg_operand" "=y")
+                               (unspec:CC [(match_operand:SI 2 "gpc_reg_operand" "r")
+                                   (match_operand 3 "immediate_operand" "n")]
                         20))])]
  ""
- "mtcrf %1,%3")
+ "*
+{
+  int mask = 0;
+  int i;
+  for (i = 0; i < XVECLEN (operands[0], 0); i++)
+    mask |= INTVAL (XVECEXP (SET_SRC (XVECEXP (operands[0], 0, i)), 0, 1));
+  operands[4] = GEN_INT (mask);
+  return \"mtcrf %4,%2\";
+}")
 
 (define_insn ""
  [(set (match_operand:CC 0 "cc_reg_operand" "=y")
@@ -13325,15 +13332,15 @@ operands[2] = GEN_INT (INTVAL (operands[1]) >> 32);
  "{lm|lmw} %1,%2")
  
 (define_insn "*return_internal_si"
-  [(use (match_operand:SI 0 "register_operand" "lc"))
-   (return)]
+  [(return)
+   (use (match_operand:SI 0 "register_operand" "lc"))]
   "TARGET_32BIT"
   "b%T0"
   [(set_attr "type" "jmpreg")])
 
 (define_insn "*return_internal_di"
-  [(use (match_operand:DI 0 "register_operand" "lc"))
-   (return)]
+  [(return)
+   (use (match_operand:DI 0 "register_operand" "lc"))]
   "TARGET_64BIT"
   "b%T0"
   [(set_attr "type" "jmpreg")])
@@ -13343,8 +13350,8 @@ operands[2] = GEN_INT (INTVAL (operands[1]) >> 32);
 
 (define_insn "*return_and_restore_fpregs_si"
  [(match_parallel 0 "any_operand"
-                  [(use (match_operand:SI 1 "register_operand" "l"))
-                  (return)
+                  [(return)
+                  (use (match_operand:SI 1 "register_operand" "l"))
                   (use (match_operand:SI 2 "call_operand" "s"))
                   (set (match_operand:DF 3 "gpc_reg_operand" "=f")
                        (match_operand:DF 4 "memory_operand" "m"))])]
@@ -13353,8 +13360,8 @@ operands[2] = GEN_INT (INTVAL (operands[1]) >> 32);
 
 (define_insn "*return_and_restore_fpregs_di"
  [(match_parallel 0 "any_operand"
-                  [(use (match_operand:DI 1 "register_operand" "l"))
-                  (return)
+                  [(return)
+                  (use (match_operand:DI 1 "register_operand" "l"))
                   (use (match_operand:DI 2 "call_operand" "s"))
                   (set (match_operand:DF 3 "gpc_reg_operand" "=f")
                        (match_operand:DF 4 "memory_operand" "m"))])]
@@ -13460,8 +13467,8 @@ operands[2] = GEN_INT (INTVAL (operands[1]) >> 32);
 
 
 (define_insn "return_eh_si"
-  [(use (match_operand:SI 0 "register_operand" "lc"))
-   (return)
+  [(return)
+   (use (match_operand:SI 0 "register_operand" "lc"))
    (use (reg:SI 2))
    (use (reg:SI 3))]
   "TARGET_32BIT"
@@ -13469,8 +13476,8 @@ operands[2] = GEN_INT (INTVAL (operands[1]) >> 32);
   [(set_attr "type" "jmpreg")])
 
 (define_insn "return_eh_di"
-  [(use (match_operand:DI 0 "register_operand" "lc"))
-   (return)
+  [(return)
+   (use (match_operand:DI 0 "register_operand" "lc"))
    (use (reg:DI 2))
    (use (reg:DI 3))]
   "TARGET_64BIT"
index 0d922c66c437ad9717eb3303427a1161e62d2869..2e1ae1450e955bd153939365055ce214f72cb380 100644 (file)
@@ -22,6 +22,7 @@ Boston, MA 02111-1307, USA.  */
 
 #include "config.h"
 #include "system.h"
+#include "toplev.h"
 #include "rtl.h"
 
 static int rtx_addr_can_trap_p PARAMS ((rtx));
@@ -878,7 +879,7 @@ single_set_1 (insn)
            /* Instruction should not consist only from USEs and CLOBBERS,
               since then gcc is allowed to remove it entirely.  In case
               something else is present, it should be first in the pattern.  */
-           abort();
+           fatal_insn ("USE or CLOBBER before SET:", insn);
 #endif
          case SET:
            break;
@@ -895,34 +896,41 @@ single_set_1 (insn)
          for (i = XVECLEN (pat, 0) - 1; i > 1; i--)
            if (GET_CODE (XVECEXP (pat, 0, i)) != USE
                && GET_CODE (XVECEXP (pat, 0, i)) != CLOBBER)
-             abort();
+             fatal_insn ("USE or CLOBBER before SET:", insn);
 #endif
            return set;
        case SET:
-         /* Multiple set insns - we are off the critical path now.  */
-         for (i = XVECLEN (pat, 0) - 1; i > 0; i--)
-           {
-             sub = XVECEXP (pat, 0, i);
-             switch GET_CODE (sub)
-               {
-               case USE:
-               case CLOBBER:
-                 break;
-
-               case SET:
-                 if (!set
-                     || (find_reg_note (insn, REG_UNUSED, SET_DEST (set))
-                         && side_effects_p (set)))
-                   set = sub;
-                 else if (! find_reg_note (insn, REG_UNUSED, SET_DEST (sub))
-                          || side_effects_p (sub))
-                   return NULL_RTX;
-                 break;
+         {
+           int seen_clobber = 0;
 
-               default:
-                 return NULL_RTX;
-               }
-           }
+           /* Multiple set insns - we are off the critical path now.  */
+           for (i = 1; i < XVECLEN (pat, 0); i++)
+             {
+               sub = XVECEXP (pat, 0, i);
+               switch GET_CODE (sub)
+                 {
+                 case USE:
+                 case CLOBBER:
+                   seen_clobber = 1;
+                   break;
+                   
+                 case SET:
+                   if (seen_clobber)
+                     fatal_insn ("USE or CLOBBER before SET:", insn);
+                   if (!set
+                       || (find_reg_note (insn, REG_UNUSED, SET_DEST (set))
+                           && side_effects_p (set)))
+                     set = sub;
+                   else if (! find_reg_note (insn, REG_UNUSED, SET_DEST (sub))
+                            || side_effects_p (sub))
+                     return NULL_RTX;
+                   break;
+                   
+                 default:
+                   return NULL_RTX;
+                 }
+             }
+         }
          return set;
        default:
          return NULL_RTX;