CANNOT_CHANGE_MODE changes for df/ra*

Michael Matz matz@suse.de
Sun Feb 2 00:48:00 GMT 2003


Hi,

this changes df.c/ra*.c to make use of the new interface of
CANNOT_CHANGE_MODE_CLASS.  It additionally adds a new flag to df.h which
will be of use later, and a fix to read_modify_subreg_p (to make GCC
bootstrap with activated new allocator).

Bootstraps without regressions on i686-linux (Ada untested).  I
additionally tested, if the new ra is still working somewhat, so it also
bootstraps without regressions when the new ra is activated by default,
when Java is deactivated.

The changes to df.* need approval.  OK for mainline?


Ciao,
Michael.
-- 
        * df.h (enum df_ref_flags.DF_REF_STRIPPED): New.
        * df.c (df_ref_record): Set DF_REF_STRIPPED.
        (read_modify_subreg_p): Narrow down cases.
        (df_def_record_1, df_uses_record): Set DF_REF_MODE_CHANGE more often.
        * ra.h (struct web): New member subreg_stripped.
        (invalid_mode_change_regs): Declare.
        * ra.c (invalid_mode_change_regs): New.
        (init_ra): Initialize it.
        * ra-build.c (init_one_web_common, remember_web_was_spilled): Use it.
        Use CANNOT_CHANGE_MODE_CLASS as ifdef guard.
        (reinit_one_web, parts_to_web_1): Deal with subreg_stripped.
        * ra-colorize.c (colorize_one_web): Use invalid_mode_change_regs.
        Use CANNOT_CHANGE_MODE_CLASS as ifdef guard.

Index: ra-colorize.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/ra-colorize.c,v
retrieving revision 1.8
diff -u -p -r1.8 ra-colorize.c
--- ra-colorize.c	17 Jan 2003 03:28:09 -0000	1.8
+++ ra-colorize.c	1 Feb 2003 22:47:53 -0000
@@ -1369,10 +1369,9 @@ colorize_one_web (web, hard)
       else
 	COPY_HARD_REG_SET (colors,
 			   usable_regs[reg_preferred_class (web->regno)]);
-#ifdef CLASS_CANNOT_CHANGE_MODE
+#ifdef CANNOT_CHANGE_MODE_CLASS
       if (web->mode_changed)
-        AND_COMPL_HARD_REG_SET (colors, reg_class_contents[
-			          (int) CLASS_CANNOT_CHANGE_MODE]);
+        AND_COMPL_HARD_REG_SET (colors, invalid_mode_change_regs);
 #endif
       COPY_HARD_REG_SET (call_clobbered, colors);
       AND_HARD_REG_SET (call_clobbered, call_used_reg_set);
@@ -1403,10 +1402,9 @@ colorize_one_web (web, hard)
 	  else
 	    IOR_HARD_REG_SET (colors, usable_regs
 			      [reg_alternate_class (web->regno)]);
-#ifdef CLASS_CANNOT_CHANGE_MODE
+#ifdef CANNOT_CHANGE_MODE_CLASS
 	  if (web->mode_changed)
-	    AND_COMPL_HARD_REG_SET (colors, reg_class_contents[
-				      (int) CLASS_CANNOT_CHANGE_MODE]);
+	    AND_COMPL_HARD_REG_SET (colors, invalid_mode_change_regs);
 #endif
 	  COPY_HARD_REG_SET (call_clobbered, colors);
 	  AND_HARD_REG_SET (call_clobbered, call_used_reg_set);
Index: ra.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/ra.c,v
retrieving revision 1.7
diff -u -p -r1.7 ra.c
--- ra.c	17 Jan 2003 03:28:09 -0000	1.7
+++ ra.c	1 Feb 2003 22:47:53 -0000
@@ -148,6 +148,7 @@ HARD_REG_SET never_use_colors;
 HARD_REG_SET usable_regs[N_REG_CLASSES];
 unsigned int num_free_regs[N_REG_CLASSES];
 HARD_REG_SET hardregs_for_mode[NUM_MACHINE_MODES];
+HARD_REG_SET invalid_mode_change_regs;
 unsigned char byte2bitcount[256];

 unsigned int debug_new_regalloc = -1;
@@ -554,6 +555,23 @@ init_ra ()
 	  }
       COPY_HARD_REG_SET (hardregs_for_mode[i], rs);
     }
+
+  CLEAR_HARD_REG_SET (invalid_mode_change_regs);
+#ifdef CANNOT_CHANGE_MODE_CLASS
+  if (0)
+  for (i = 0; i < NUM_MACHINE_MODES; i++)
+    {
+      enum machine_mode from = (enum machine_mode) i;
+      enum machine_mode to;
+      for (to = VOIDmode; to < MAX_MACHINE_MODE; ++to)
+	{
+	  int r;
+	  for (r = 0; r < FIRST_PSEUDO_REGISTER; r++)
+	    if (REG_CANNOT_CHANGE_MODE_P (from, to, r))
+	      SET_HARD_REG_BIT (invalid_mode_change_regs, r);
+	}
+    }
+#endif

   for (an_unusable_color = 0; an_unusable_color < FIRST_PSEUDO_REGISTER;
        an_unusable_color++)
Index: ra.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/ra.h,v
retrieving revision 1.5
diff -u -p -r1.5 ra.h
--- ra.h	17 Jan 2003 03:28:09 -0000	1.5
+++ ra.h	1 Feb 2003 22:47:53 -0000
@@ -168,6 +168,11 @@ struct web
      was illegal for hardregs in CLASS_CANNOT_CHANGE_MODE.  */
   unsigned int mode_changed:1;

+  /* Nonzero if some references of this web, where in subreg context,
+     but the actual subreg is already stripped (i.e. we don't know the
+     outer mode of the actual reference).  */
+  unsigned int subreg_stripped:1;
+
   /* Nonzero, when this web stems from the last pass of the allocator,
      and all info is still valid (i.e. it wasn't spilled).  */
   unsigned int old_web:1;
@@ -497,6 +502,8 @@ extern unsigned int num_free_regs[N_REG_
    represent the possible resources which could be taken away be a value
    in mode M.  */
 extern HARD_REG_SET hardregs_for_mode[NUM_MACHINE_MODES];
+/* The set of hardregs, for which _any_ mode change is invalid.  */
+extern HARD_REG_SET invalid_mode_change_regs;
 /* For 0 <= I <= 255, the number of bits set in I.  Used to calculate
    the number of set bits in a HARD_REG_SET.  */
 extern unsigned char byte2bitcount[256];
Index: ra-build.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/ra-build.c,v
retrieving revision 1.15
diff -u -p -r1.15 ra-build.c
--- ra-build.c	18 Jan 2003 03:07:26 -0000	1.15
+++ ra-build.c	1 Feb 2003 22:47:53 -0000
@@ -1305,10 +1305,9 @@ init_one_web_common (web, reg)
       AND_COMPL_HARD_REG_SET (web->usable_regs, never_use_colors);
       prune_hardregs_for_mode (&web->usable_regs,
 			       PSEUDO_REGNO_MODE (web->regno));
-#ifdef CLASS_CANNOT_CHANGE_MODE
+#ifdef CANNOT_CHANGE_MODE_CLASS
       if (web->mode_changed)
-        AND_COMPL_HARD_REG_SET (web->usable_regs, reg_class_contents[
-			          (int) CLASS_CANNOT_CHANGE_MODE]);
+        AND_COMPL_HARD_REG_SET (web->usable_regs, invalid_mode_change_regs);
 #endif
       web->num_freedom = hard_regs_count (web->usable_regs);
       web->num_freedom -= web->add_hardregs;
@@ -1351,6 +1350,7 @@ reinit_one_web (web, reg)
   web->artificial = 0;
   web->live_over_abnormal = 0;
   web->mode_changed = 0;
+  web->subreg_stripped = 0;
   web->move_related = 0;
   web->in_load = 0;
   web->target_of_spilled_move = 0;
@@ -1908,6 +1908,9 @@ parts_to_webs_1 (df, copy_webs, all_refs
 	  if ((DF_REF_FLAGS (ref) & DF_REF_MODE_CHANGE) != 0
 	      && web->regno >= FIRST_PSEUDO_REGISTER)
 	    web->mode_changed = 1;
+	  if ((DF_REF_FLAGS (ref) & DF_REF_STRIPPED) != 0
+	      && web->regno >= FIRST_PSEUDO_REGISTER)
+	    web->subreg_stripped = 1;
 	  if (i >= def_id
 	      && TEST_BIT (live_over_abnormal, ref_id))
 	    web->live_over_abnormal = 1;
@@ -1957,6 +1960,9 @@ parts_to_webs_1 (df, copy_webs, all_refs
       if ((DF_REF_FLAGS (ref) & DF_REF_MODE_CHANGE) != 0
 	  && web->regno >= FIRST_PSEUDO_REGISTER)
 	web->mode_changed = 1;
+      if ((DF_REF_FLAGS (ref) & DF_REF_STRIPPED) != 0
+	  && web->regno >= FIRST_PSEUDO_REGISTER)
+	web->subreg_stripped = 1;

       /* Setup def2web, or use2web, and increment num_defs or num_uses.  */
       if (i < def_id)
@@ -2360,10 +2366,9 @@ remember_web_was_spilled (web)
 		       reg_class_contents[(int) GENERAL_REGS]);
   AND_COMPL_HARD_REG_SET (web->usable_regs, never_use_colors);
   prune_hardregs_for_mode (&web->usable_regs, PSEUDO_REGNO_MODE (web->regno));
-#ifdef CLASS_CANNOT_CHANGE_MODE
+#ifdef CANNOT_CHANGE_MODE_CLASS
   if (web->mode_changed)
-    AND_COMPL_HARD_REG_SET (web->usable_regs, reg_class_contents[
-			      (int) CLASS_CANNOT_CHANGE_MODE]);
+    AND_COMPL_HARD_REG_SET (web->usable_regs, invalid_mode_change_regs);
 #endif
   web->num_freedom = hard_regs_count (web->usable_regs);
   if (!web->num_freedom)
Index: df.h
===================================================================
RCS file: /cvs/gcc/gcc/gcc/df.h,v
retrieving revision 1.15
diff -u -p -r1.15 df.h
--- df.h	26 Jan 2003 06:10:37 -0000	1.15
+++ df.h	1 Feb 2003 22:47:53 -0000
@@ -52,13 +52,17 @@ enum df_ref_flags
     DF_REF_READ_WRITE = 1,

     /* This flag is set on register references inside a subreg on
-       machines which have CLASS_CANNOT_CHANGE_MODE and where the mode
-       change of that subreg expression is invalid for this class.
+       machines which have CANNOT_CHANGE_MODE_CLASS.
        Note, that this flag can also be set on df_refs representing
        the REG itself (i.e., one might not see the subreg anyore).
        Also note, that this flag is set also for hardreg refs, i.e.,
        you must check yourself if it's a pseudo.  */
-    DF_REF_MODE_CHANGE = 2
+    DF_REF_MODE_CHANGE = 2,
+
+    /* This flag is set, if we stripped the subreg from the reference.
+       In this case we must make conservative guesses, at what the
+       outer mode was.  */
+    DF_REF_STRIPPED = 4
   };


Index: df.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/df.c,v
retrieving revision 1.46
diff -u -p -r1.46 df.c
--- df.c	31 Jan 2003 23:34:12 -0000	1.46
+++ df.c	1 Feb 2003 22:47:53 -0000
@@ -849,6 +849,7 @@ df_ref_record (df, reg, loc, insn, ref_t
     {
       loc = &SUBREG_REG (reg);
       reg = *loc;
+      ref_flags |= DF_REF_STRIPPED;
     }

   regno = REGNO (GET_CODE (reg) == SUBREG ? SUBREG_REG (reg) : reg);
@@ -893,11 +894,12 @@ read_modify_subreg_p (x)
     return false;
   isize = GET_MODE_SIZE (GET_MODE (SUBREG_REG (x)));
   osize = GET_MODE_SIZE (GET_MODE (x));
+  /* Paradoxical subreg writes don't leave a trace of the old content.  */
   if (isize <= osize)
-    return true;
+    return false;
   if (isize <= UNITS_PER_WORD)
     return false;
-  if (osize > UNITS_PER_WORD)
+  if (osize >= UNITS_PER_WORD)
     return false;
   return true;
 }
@@ -927,9 +929,7 @@ df_def_record_1 (df, x, bb, insn)
     }

 #ifdef CLASS_CANNOT_CHANGE_MODE
-  if (GET_CODE (dst) == SUBREG
-      && CLASS_CANNOT_CHANGE_MODE_P (GET_MODE (SUBREG_REG (dst)),
-				     GET_MODE (dst)))
+  if (GET_CODE (dst) == SUBREG)
     flags |= DF_REF_MODE_CHANGE;
 #endif

@@ -948,9 +948,7 @@ df_def_record_1 (df, x, bb, insn)
 	  dst = *loc;
 	}
 #ifdef CLASS_CANNOT_CHANGE_MODE
-      if (GET_CODE (dst) == SUBREG
-	  && CLASS_CANNOT_CHANGE_MODE_P (GET_MODE (SUBREG_REG (dst)),
-				         GET_MODE (dst)))
+      if (GET_CODE (dst) == SUBREG)
         flags |= DF_REF_MODE_CHANGE;
 #endif
       loc = &XEXP (dst, 0);
@@ -1050,9 +1048,7 @@ df_uses_record (df, loc, ref_type, bb, i
 	  return;
 	}
 #ifdef CLASS_CANNOT_CHANGE_MODE
-      if (CLASS_CANNOT_CHANGE_MODE_P (GET_MODE (x),
-				      GET_MODE (SUBREG_REG (x))))
-        flags |= DF_REF_MODE_CHANGE;
+      flags |= DF_REF_MODE_CHANGE;
 #endif

       /* ... Fall through ...  */
@@ -1076,9 +1072,7 @@ df_uses_record (df, loc, ref_type, bb, i
 		{
 		  use_flags = DF_REF_READ_WRITE;
 #ifdef CLASS_CANNOT_CHANGE_MODE
-		  if (CLASS_CANNOT_CHANGE_MODE_P (GET_MODE (dst),
-						  GET_MODE (SUBREG_REG (dst))))
-		    use_flags |= DF_REF_MODE_CHANGE;
+		  use_flags |= DF_REF_MODE_CHANGE;
 #endif
 		  df_uses_record (df, &SUBREG_REG (dst), DF_REF_REG_USE, bb,
 				  insn, use_flags);
@@ -1102,9 +1096,7 @@ df_uses_record (df, loc, ref_type, bb, i
 		abort ();
 	      use_flags = DF_REF_READ_WRITE;
 #ifdef CLASS_CANNOT_CHANGE_MODE
-	      if (CLASS_CANNOT_CHANGE_MODE_P (GET_MODE (dst),
-					      GET_MODE (SUBREG_REG (dst))))
-		use_flags |= DF_REF_MODE_CHANGE;
+	      use_flags |= DF_REF_MODE_CHANGE;
 #endif
 	      df_uses_record (df, &SUBREG_REG (dst), DF_REF_REG_USE, bb,
 			     insn, use_flags);



More information about the Gcc-patches mailing list