[dataflow][PATCH] Fix a regression on ia64 - subregs_of_mode cleanup

Seongbae Park seongbae.park@gmail.com
Wed Mar 14 00:58:00 GMT 2007


Hi,

This patch fixes a regression on ia64 which was due to
subregs_of_mode not being up-to-date when used.
Since I couldn't find any use of subregs_of_mode
other than local and global allocs,
I've moved subregs_of_mode_init just before local-alloc
created a new subregs_of_mode_finish after global-alloc,
and added extra assertions to make sure
it is only used when valid,
to prevent other passes from accidentally using it.
Bootstrapped and regtested on ia64.

2007-03-13  Seongbae Park <seongbae.park@gmail.com>

        * tree-pass.h (pass_subregs_of_mode_finish): New pass declaration.
        * regclass.c (record_subregs_of_mode): Made static, and
         moved before init_subregs_of_mode to compile.
         (cannot_change_mode_set_regs, invalid_mode_change_p):
         Added assertion.
         (finish_subregs_of_mode): New function.
         (pass_subregs_of_mode_finish): New pass.
         * rtl.h (record_subregs_of_mode): Removed.
         * combine.c (gen_lowpart_for_combine): Removed
          calls to record_subregs_of_mode.
         * passes.c (init_optimization_passes): Moved pass_subregs_of_mode_init
           just before local_alloc. New pass pass_subregs_of_mode_finish
           after global_alloc.

-- 
#pragma ident "Seongbae Park, compiler, http://seongbae.blogspot.com"
-------------- next part --------------
Index: tree-pass.h
===================================================================
--- tree-pass.h	(revision 122890)
+++ tree-pass.h	(working copy)
@@ -370,6 +370,7 @@ extern struct tree_opt_pass pass_cse2;
 extern struct tree_opt_pass pass_df_initialize;
 extern struct tree_opt_pass pass_regclass_init;
 extern struct tree_opt_pass pass_subregs_of_mode_init;
+extern struct tree_opt_pass pass_subregs_of_mode_finish;
 extern struct tree_opt_pass pass_inc_dec;
 extern struct tree_opt_pass pass_no_new_pseudos;
 extern struct tree_opt_pass pass_stack_ptr_mod;
Index: regclass.c
===================================================================
--- regclass.c	(revision 122890)
+++ regclass.c	(working copy)
@@ -2677,6 +2677,38 @@ som_eq (const void *x, const void *y)
 }
 
 
+static void
+record_subregs_of_mode (rtx subreg)
+{
+  struct subregs_of_mode_node dummy, *node;
+  enum machine_mode mode;
+  unsigned int regno;
+  void **slot;
+
+  if (!REG_P (SUBREG_REG (subreg)))
+    return;
+
+  regno = REGNO (SUBREG_REG (subreg));
+  mode = GET_MODE (subreg);
+
+  if (regno < FIRST_PSEUDO_REGISTER)
+    return;
+
+  dummy.block = regno & -8;
+  slot = htab_find_slot_with_hash (subregs_of_mode, &dummy,
+				   dummy.block, INSERT);
+  node = *slot;
+  if (node == NULL)
+    {
+      node = XCNEW (struct subregs_of_mode_node);
+      node->block = regno & -8;
+      *slot = node;
+    }
+
+  node->modes[mode] |= 1 << (regno & 7);
+}
+
+
 /* Call record_subregs_of_mode for all the subregs in X.  */
 
 static void 
@@ -2722,36 +2754,6 @@ init_subregs_of_mode (void)
   return 0;
 }
 
-void
-record_subregs_of_mode (rtx subreg)
-{
-  struct subregs_of_mode_node dummy, *node;
-  enum machine_mode mode;
-  unsigned int regno;
-  void **slot;
-
-  if (!REG_P (SUBREG_REG (subreg)))
-    return;
-
-  regno = REGNO (SUBREG_REG (subreg));
-  mode = GET_MODE (subreg);
-
-  if (regno < FIRST_PSEUDO_REGISTER)
-    return;
-
-  dummy.block = regno & -8;
-  slot = htab_find_slot_with_hash (subregs_of_mode, &dummy,
-				   dummy.block, INSERT);
-  node = *slot;
-  if (node == NULL)
-    {
-      node = XCNEW (struct subregs_of_mode_node);
-      node->block = regno & -8;
-      *slot = node;
-    }
-
-  node->modes[mode] |= 1 << (regno & 7);
-}
 
 /* Set bits in *USED which correspond to registers which can't change
    their mode from FROM to any mode in which REGNO was encountered.  */
@@ -2765,6 +2767,7 @@ cannot_change_mode_set_regs (HARD_REG_SE
   unsigned char mask;
   unsigned int i;
 
+  gcc_assert (subregs_of_mode);
   dummy.block = regno & -8;
   node = htab_find_with_hash (subregs_of_mode, &dummy, dummy.block);
   if (node == NULL)
@@ -2790,6 +2793,7 @@ invalid_mode_change_p (unsigned int regn
   enum machine_mode to;
   unsigned char mask;
 
+  gcc_assert (subregs_of_mode);
   dummy.block = regno & -8;
   node = htab_find_with_hash (subregs_of_mode, &dummy, dummy.block);
   if (node == NULL)
@@ -2803,12 +2807,25 @@ invalid_mode_change_p (unsigned int regn
 
   return false;
 }
+
+static unsigned int
+finish_subregs_of_mode (void)
+{
+  htab_delete (subregs_of_mode);
+  subregs_of_mode = 0;
+  return 0;
+}
 #else
 static unsigned int
 init_subregs_of_mode (void)
 {
   return 0;
 }
+static unsigned int
+finish_subregs_of_mode (void)
+{
+  return 0;
+}
 
 #endif /* CANNOT_CHANGE_MODE_CLASS */
 
@@ -2839,6 +2856,23 @@ struct tree_opt_pass pass_subregs_of_mod
   0                                     /* letter */
 };
 
+struct tree_opt_pass pass_subregs_of_mode_finish =
+{
+  "subregs_of_mode_finish",               /* name */
+  gate_subregs_of_mode_init,            /* gate */
+  finish_subregs_of_mode,               /* execute */
+  NULL,                                 /* sub */
+  NULL,                                 /* next */
+  0,                                    /* static_pass_number */
+  0,                                    /* tv_id */
+  0,                                    /* properties_required */
+  0,                                    /* properties_provided */
+  0,                                    /* properties_destroyed */
+  0,                                    /* todo_flags_start */
+  0,                                    /* todo_flags_finish */
+  0                                     /* letter */
+};
+
 
 
 #include "gt-regclass.h"
Index: rtl.h
===================================================================
--- rtl.h	(revision 122890)
+++ rtl.h	(working copy)
@@ -2156,7 +2156,6 @@ extern void regclass (rtx, int);
 extern void reg_scan (rtx, unsigned int);
 extern void reg_scan_update (rtx, rtx, unsigned int);
 extern void fix_register (const char *, int, int);
-extern void record_subregs_of_mode (rtx);
 #ifdef HARD_CONST
 extern void cannot_change_mode_set_regs (HARD_REG_SET *,
 					 enum machine_mode, unsigned int);
Index: combine.c
===================================================================


More information about the Gcc-patches mailing list