Make ifcvt clean up dead comparisons
authorRichard Sandiford <richard.sandiford@arm.com>
Thu, 18 Jul 2019 08:24:16 +0000 (08:24 +0000)
committerRichard Sandiford <rsandifo@gcc.gnu.org>
Thu, 18 Jul 2019 08:24:16 +0000 (08:24 +0000)
This change is needed to avoid a regression in gcc.dg/ifcvt-3.c
for a later patch.  Without it, we enter CSE with a dead comparison left
by if-conversion and then eliminate the second (live) comparison in
favour of the dead one.  That's functionally correct in itself, but it
meant that we'd combine the subtraction and comparison into a SUBS
before we have a chance to fold away the subtraction.

2019-07-18  Richard Sandiford  <richard.sandiford@arm.com>

gcc/
* basic-block.h (CLEANUP_FORCE_FAST_DCE): New macro.
* cfgcleanup.c (cleanup_cfg): Call run_fast_dce if
CLEANUP_FORCE_FAST_DCE is set.
* ifcvt.c (rest_of_handle_if_conversion): Pass
CLEANUP_FORCE_FAST_DCE to the final cleanup_cfg call if
if-conversion succeeded.

From-SVN: r273569

gcc/ChangeLog
gcc/basic-block.h
gcc/cfgcleanup.c
gcc/ifcvt.c

index 76baf87..b545a03 100644 (file)
@@ -1,3 +1,12 @@
+2019-07-18  Richard Sandiford  <richard.sandiford@arm.com>
+
+       * basic-block.h (CLEANUP_FORCE_FAST_DCE): New macro.
+       * cfgcleanup.c (cleanup_cfg): Call run_fast_dce if
+       CLEANUP_FORCE_FAST_DCE is set.
+       * ifcvt.c (rest_of_handle_if_conversion): Pass
+       CLEANUP_FORCE_FAST_DCE to the final cleanup_cfg call if
+       if-conversion succeeded.
+
 2019-07-18  Richard Biener  <rguenther@suse.de>
 
        * tree-ssa-sccvn.c (vn_walk_cb_data::push_partial_def): Refactor
index 5e0fbc0..2a0e826 100644 (file)
@@ -508,6 +508,8 @@ ei_cond (edge_iterator ei, edge *p)
 #define CLEANUP_CFGLAYOUT      32      /* Do cleanup in cfglayout mode.  */
 #define CLEANUP_CFG_CHANGED    64      /* The caller changed the CFG.  */
 #define CLEANUP_NO_PARTITIONING        128     /* Do not try to fix partitions.  */
+#define CLEANUP_FORCE_FAST_DCE 0x100   /* Force run_fast_dce to be called
+                                          at least once.  */
 
 /* Return true if BB is in a transaction.  */
 
index fca3a08..b930763 100644 (file)
@@ -3193,7 +3193,10 @@ cleanup_cfg (int mode)
              && !delete_trivially_dead_insns (get_insns (), max_reg_num ()))
            break;
          if ((mode & CLEANUP_CROSSJUMP) && crossjumps_occurred)
-           run_fast_dce ();
+           {
+             run_fast_dce ();
+             mode &= ~CLEANUP_FORCE_FAST_DCE;
+           }
        }
       else
        break;
@@ -3202,6 +3205,9 @@ cleanup_cfg (int mode)
   if (mode & CLEANUP_CROSSJUMP)
     remove_fake_exit_edges ();
 
+  if (mode & CLEANUP_FORCE_FAST_DCE)
+    run_fast_dce ();
+
   /* Don't call delete_dead_jumptables in cfglayout mode, because
      that function assumes that jump tables are in the insns stream.
      But we also don't _have_ to delete dead jumptables in cfglayout
index 7b2f6e6..e0c9522 100644 (file)
@@ -5457,6 +5457,8 @@ if_convert (bool after_combine)
 static unsigned int
 rest_of_handle_if_conversion (void)
 {
+  int flags = 0;
+
   if (flag_if_conversion)
     {
       if (dump_file)
@@ -5466,9 +5468,12 @@ rest_of_handle_if_conversion (void)
        }
       cleanup_cfg (CLEANUP_EXPENSIVE);
       if_convert (false);
+      if (num_updated_if_blocks)
+       /* Get rid of any dead CC-related instructions.  */
+       flags |= CLEANUP_FORCE_FAST_DCE;
     }
 
-  cleanup_cfg (0);
+  cleanup_cfg (flags);
   return 0;
 }