]> git.ipfire.org Git - thirdparty/gcc.git/commitdiff
reload1.c (forget_old_reloads_1): Keep track of the largest mode found while strippin...
authorJeffrey A Law <law@cygnus.com>
Thu, 27 Aug 1998 22:48:14 +0000 (22:48 +0000)
committerJeff Law <law@gcc.gnu.org>
Thu, 27 Aug 1998 22:48:14 +0000 (16:48 -0600)
        * reload1.c (forget_old_reloads_1): Keep track of the largest mode
        found while stripping SUBREGS and invalidate reloads for all the hard
        regs specified by that largest mode.  egcs-1.1 only hack.  The
        mainline tree will get a better fix.

From-SVN: r22041

gcc/ChangeLog
gcc/reload1.c

index 0a71494ec2069e7cba9f5446c62b96f2733d7cad..75b8928246b9160989560f4e3034233aef1275cb 100644 (file)
@@ -1,3 +1,10 @@
+Thu Aug 27 23:44:49 1998  Jeffrey A Law  (law@cygnus.com)
+
+       * reload1.c (forget_old_reloads_1): Keep track of the largest mode
+       found while stripping SUBREGS and invalidate reloads for all the hard
+       regs specified by that largest mode.  egcs-1.1 only hack.  The
+       mainline tree will get a better fix.
+
 Tue Aug 25 19:43:11 1998  Jeffrey A Law  (law@cygnus.com)
 
        * From Alexandre:
index 239afd82df0f818eed40bd172f02e443addc58da..c2987bbff7fd79886711df50cff37e2923d73200 100644 (file)
@@ -4251,27 +4251,43 @@ forget_old_reloads_1 (x, ignored)
      rtx ignored ATTRIBUTE_UNUSED;
 {
   register int regno;
+  enum machine_mode mode = GET_MODE (x);
   int nr;
-  int offset = 0;
 
-  /* note_stores does give us subregs of hard regs.  */
+  /* note_stores does give us subregs of hard regs.
+
+     This is a egcs-1.1 tree hack only.  A better solution is being
+     developed for mainline sources.  Do not import this back to the
+     mainline tree.
+
+     We want to strip all the SUBREGs, but also keep track of the
+     largest mode we encounter so that we can invalidate all the
+     hard regs which are needed to hold the widest mode.
+
+     This avoids a bug in choose_reload_regs (which is where the real
+     fix for the mainline tree will be).  */
+
   while (GET_CODE (x) == SUBREG)
     {
-      offset += SUBREG_WORD (x);
+      if (GET_MODE_BITSIZE (GET_MODE (x)) > GET_MODE_BITSIZE (mode))
+       mode = GET_MODE (x);
       x = SUBREG_REG (x);
     }
 
+  if (GET_MODE_BITSIZE (GET_MODE (x)) > GET_MODE_BITSIZE (mode))
+    mode = GET_MODE (x);
+
   if (GET_CODE (x) != REG)
     return;
 
-  regno = REGNO (x) + offset;
+  regno = REGNO (x);
 
   if (regno >= FIRST_PSEUDO_REGISTER)
     nr = 1;
   else
     {
       int i;
-      nr = HARD_REGNO_NREGS (regno, GET_MODE (x));
+      nr = HARD_REGNO_NREGS (regno, mode);
       /* Storing into a spilled-reg invalidates its contents.
         This can happen if a block-local pseudo is allocated to that reg
         and it wasn't spilled because this block's total need is 0.