The following fixes PR61438 - when moving the PHI insertion inhibiting
code I forgot to guard it so that it only runs for PRE.

Bootstrap/regtest pending on x86_64-unknown-linux-gnu.

Richard.

2014-06-10  Richard Biener  <rguent...@suse.de>

        PR tree-optimization/61438
        * tree-ssa-pre.c (eliminate_dom_walker): Add do_pre member.
        (eliminate_dom_walker::before_dom_children): Only try to inhibit
        insertion of IVs if running PRE.
        (eliminate): Adjust.
        (pass_pre::execute): Likewise.
        (pass_fre::execute): Likewise.

        * gcc.dg/torture/pr61438.c: New testcase.

Index: gcc/tree-ssa-pre.c
===================================================================
*** gcc/tree-ssa-pre.c  (revision 211398)
--- gcc/tree-ssa-pre.c  (working copy)
*************** eliminate_insert (gimple_stmt_iterator *
*** 3992,4001 ****
  class eliminate_dom_walker : public dom_walker
  {
  public:
!   eliminate_dom_walker (cdi_direction direction) : dom_walker (direction) {}
  
    virtual void before_dom_children (basic_block);
    virtual void after_dom_children (basic_block);
  };
  
  /* Perform elimination for the basic-block B during the domwalk.  */
--- 3992,4004 ----
  class eliminate_dom_walker : public dom_walker
  {
  public:
!   eliminate_dom_walker (cdi_direction direction, bool do_pre_)
!       : dom_walker (direction), do_pre (do_pre_) {}
  
    virtual void before_dom_children (basic_block);
    virtual void after_dom_children (basic_block);
+ 
+   bool do_pre;
  };
  
  /* Perform elimination for the basic-block B during the domwalk.  */
*************** eliminate_dom_walker::before_dom_childre
*** 4192,4198 ****
                 variable.  In other cases the vectorizer won't do anything
                 anyway (either it's loop invariant or a complicated
                 expression).  */
!             if (flag_tree_loop_vectorize
                  && gimple_assign_single_p (stmt)
                  && TREE_CODE (sprime) == SSA_NAME
                  && loop_outer (b->loop_father))
--- 4195,4202 ----
                 variable.  In other cases the vectorizer won't do anything
                 anyway (either it's loop invariant or a complicated
                 expression).  */
!             if (do_pre
!                 && flag_tree_loop_vectorize
                  && gimple_assign_single_p (stmt)
                  && TREE_CODE (sprime) == SSA_NAME
                  && loop_outer (b->loop_father))
*************** eliminate_dom_walker::after_dom_children
*** 4434,4440 ****
  /* Eliminate fully redundant computations.  */
  
  static unsigned int
! eliminate (void)
  {
    gimple_stmt_iterator gsi;
    gimple stmt;
--- 4438,4444 ----
  /* Eliminate fully redundant computations.  */
  
  static unsigned int
! eliminate (bool do_pre)
  {
    gimple_stmt_iterator gsi;
    gimple stmt;
*************** eliminate (void)
*** 4448,4454 ****
    el_avail.create (0);
    el_avail_stack.create (0);
  
!   eliminate_dom_walker (CDI_DOMINATORS).walk (cfun->cfg->x_entry_block_ptr);
  
    el_avail.release ();
    el_avail_stack.release ();
--- 4452,4459 ----
    el_avail.create (0);
    el_avail_stack.create (0);
  
!   eliminate_dom_walker (CDI_DOMINATORS,
!                       do_pre).walk (cfun->cfg->x_entry_block_ptr);
  
    el_avail.release ();
    el_avail_stack.release ();
*************** pass_pre::execute (function *fun)
*** 4779,4785 ****
    gsi_commit_edge_inserts ();
  
    /* Remove all the redundant expressions.  */
!   todo |= eliminate ();
  
    statistics_counter_event (fun, "Insertions", pre_stats.insertions);
    statistics_counter_event (fun, "PA inserted", pre_stats.pa_insert);
--- 4784,4790 ----
    gsi_commit_edge_inserts ();
  
    /* Remove all the redundant expressions.  */
!   todo |= eliminate (true);
  
    statistics_counter_event (fun, "Insertions", pre_stats.insertions);
    statistics_counter_event (fun, "PA inserted", pre_stats.pa_insert);
*************** pass_fre::execute (function *fun)
*** 4864,4870 ****
    memset (&pre_stats, 0, sizeof (pre_stats));
  
    /* Remove all the redundant expressions.  */
!   todo |= eliminate ();
  
    todo |= fini_eliminate ();
  
--- 4869,4875 ----
    memset (&pre_stats, 0, sizeof (pre_stats));
  
    /* Remove all the redundant expressions.  */
!   todo |= eliminate (false);
  
    todo |= fini_eliminate ();
  
Index: gcc/testsuite/gcc.dg/torture/pr61438.c
===================================================================
*** gcc/testsuite/gcc.dg/torture/pr61438.c      (revision 0)
--- gcc/testsuite/gcc.dg/torture/pr61438.c      (working copy)
***************
*** 0 ****
--- 1,48 ----
+ /* { dg-do run } */
+ 
+ extern void abort (void);
+ 
+ int a, c, **d, e, g;
+ static int b = 1;
+ 
+ struct
+ {
+   int f0;
+ } f;
+ 
+ void
+ foo ()
+ {
+   int h, *i = &a;
+   for (; e;)
+     {
+       for (c = 0; c < 1; c++)
+       for (; b;)
+         ;
+       for (;;)
+       {
+         if (a)
+           {
+             for (; f.f0; f.f0++)
+               ;
+             if (g)
+               break;
+           }
+         for (h = 0; h < 2; h++)
+           {
+             i = *d;
+             if (!i)
+               abort ();
+           }
+       }
+     }
+   if (!i)
+     abort ();
+ }
+ 
+ int
+ main ()
+ {
+   foo (); 
+   return 0;
+ }

Reply via email to