[Bug tree-optimization/77975] [6/7 Regression] Missed optimization for some small constants

2017-03-09 Thread jakub at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=77975

--- Comment #6 from Jakub Jelinek  ---
Author: jakub
Date: Fri Mar 10 07:53:57 2017
New Revision: 246021

URL: https://gcc.gnu.org/viewcvs?rev=246021=gcc=rev
Log:
PR tree-optimization/77975
* tree-ssa-loop-niter.c (get_base_for): Allow phi argument from latch
edge to be constant.
(get_val_for): For constant x return it.  Formatting fix.
(loop_niter_by_eval): Avoid pointless looping if the next iteration
would use the same bases as the current one.

* gcc.dg/pr77975.c: New test.

Added:
trunk/gcc/testsuite/gcc.dg/pr77975.c
Modified:
trunk/gcc/ChangeLog
trunk/gcc/testsuite/ChangeLog
trunk/gcc/tree-ssa-loop-niter.c

[Bug tree-optimization/77975] [6/7 Regression] Missed optimization for some small constants

2017-03-09 Thread rguenther at suse dot de
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=77975

--- Comment #5 from rguenther at suse dot de  ---
On Thu, 9 Mar 2017, jakub at gcc dot gnu.org wrote:

> https://gcc.gnu.org/bugzilla/show_bug.cgi?id=77975
> 
> Jakub Jelinek  changed:
> 
>What|Removed |Added
> 
>  CC||jakub at gcc dot gnu.org
> 
> --- Comment #4 from Jakub Jelinek  ---
> Created attachment 40936
>   --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=40936=edit
> gcc7-pr77975.patch
> 
> Actually I think your patch is fully correct.

It's been some time but I think I have tested my patch and it
failed somewhere, but maybe I just thought it was too simple.

[Bug tree-optimization/77975] [6/7 Regression] Missed optimization for some small constants

2017-03-09 Thread jakub at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=77975

Jakub Jelinek  changed:

   What|Removed |Added

 CC||jakub at gcc dot gnu.org

--- Comment #4 from Jakub Jelinek  ---
Created attachment 40936
  --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=40936=edit
gcc7-pr77975.patch

Actually I think your patch is fully correct.  If next[j] (the phi argument
from the latch edge) is constant in addition to val[j] (the phi argument from
preheader edge), then in the val[j] = get_val_for (next[j], val[j]); we want to
set val[j] = next[j];, the processing of the statements in the loop is then
done in the other get_val_for call - the aval[j] = get_val_for (op[j], val[j]);
So, the first time we evaluate the statements for base of val[j] and second
time for base of next[j] if both are constants.  The only thing I've added in
addition to some comment/formatting changes and testcase is a compile time
optimization, MAX_ITERATIONS_TO_TRACK can be very large (I'm surprised we don't
limit also the number of statements between op and the header phi node, there
could be hundreds of thousands of them), but if the phi contains two same
constants, then it is enough to do one iteration of the loop, if two different
constants, then two, all further work is wasted.

[Bug tree-optimization/77975] [6/7 Regression] Missed optimization for some small constants

2016-12-21 Thread jakub at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=77975

Jakub Jelinek  changed:

   What|Removed |Added

   Target Milestone|6.3 |6.4

--- Comment #3 from Jakub Jelinek  ---
GCC 6.3 is being released, adjusting target milestone.

[Bug tree-optimization/77975] [6/7 Regression] Missed optimization for some small constants

2016-12-06 Thread rguenth at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=77975

Richard Biener  changed:

   What|Removed |Added

   Priority|P3  |P2
 CC||rguenth at gcc dot gnu.org

[Bug tree-optimization/77975] [6/7 Regression] Missed optimization for some small constants

2016-10-14 Thread rguenth at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=77975

--- Comment #2 from Richard Biener  ---
> Proved that loop 1 iterates 2 times using brute force.

so the question is why that doesn't work for the new form (and this is what we
should fix).  Because

static gphi *
get_base_for (struct loop *loop, tree x)
{
...
  init = PHI_ARG_DEF_FROM_EDGE (phi, loop_preheader_edge (loop));
  next = PHI_ARG_DEF_FROM_EDGE (phi, loop_latch_edge (loop));

  if (TREE_CODE (next) != SSA_NAME)
return NULL;

Index: gcc/tree-ssa-loop-niter.c
===
--- gcc/tree-ssa-loop-niter.c   (revision 241148)
+++ gcc/tree-ssa-loop-niter.c   (working copy)
@@ -2545,13 +2551,11 @@ get_base_for (struct loop *loop, tree x)
   init = PHI_ARG_DEF_FROM_EDGE (phi, loop_preheader_edge (loop));
   next = PHI_ARG_DEF_FROM_EDGE (phi, loop_latch_edge (loop));

-  if (TREE_CODE (next) != SSA_NAME)
-return NULL;
-
   if (!is_gimple_min_invariant (init))
 return NULL;

-  if (chain_of_csts_start (loop, next) != phi)
+  if (TREE_CODE (next) == SSA_NAME
+  && chain_of_csts_start (loop, next) != phi)
 return NULL;

   return phi;
@@ -2574,6 +2578,8 @@ get_val_for (tree x, tree base)

   if (!x)
 return base;
+  else if (is_gimple_min_invariant (x))
+return x;

   stmt = SSA_NAME_DEF_STMT (x);
   if (gimple_code (stmt) == GIMPLE_PHI)


fixes it.  But I think it's not correct as it misses the intermediate stmt
evaluations.  Some more refactoring (passing in the PHI def to get_val_for)
is necessary I think.

[Bug tree-optimization/77975] [6/7 Regression] Missed optimization for some small constants

2016-10-14 Thread marxin at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=77975

Martin Liška  changed:

   What|Removed |Added

 Status|UNCONFIRMED |NEW
   Last reconfirmed||2016-10-14
 CC||law at gcc dot gnu.org,
   ||marxin at gcc dot gnu.org
 Ever confirmed|0   |1
  Known to fail||6.1.0, 7.0

--- Comment #1 from Martin Liška  ---
Confirmed, started with r232361. IV canon can't identify number of iterations:

Before:
;; Function f7 (f7, funcdef_no=11, decl_uid=2279, cgraph_uid=11,
symbol_order=11)

Proved that loop 1 iterates 2 times using brute force.
Loop 1 iterates 2 times.
Loop 1 iterates at most 2 times.
Loop 1 likely iterates at most 2 times.
Added canonical iv to loop 1, 2 iterations.
f7 ()
{
  unsigned int a;
  unsigned int c;
  struct _IO_FILE * stderr.0_1;
  unsigned int ivtmp_2;
  unsigned int ivtmp_3;

  :

  :
  # c_14 = PHI 
  # a_15 = PHI 
  # ivtmp_3 = PHI 
  a_5 = a_15 >> 1;
  c_6 = c_14 + 1;
  ivtmp_2 = ivtmp_3 - 1;
  if (ivtmp_2 != 0)
goto ;
  else
goto ;

  :
  goto ;

  :
  # c_4 = PHI 
  stderr.0_1 = stderr;
  fprintf (stderr.0_1, "cnt: %d\n", c_4);
  return 0;

}


After:
;; Function f7 (f7, funcdef_no=11, decl_uid=2279, cgraph_uid=11,
symbol_order=11)

f7 ()
{
  unsigned int a;
  unsigned int c;
  struct _IO_FILE * stderr.0_1;

  :

  :
  # c_14 = PHI 
  # a_15 = PHI <1(4), 3(2)>
  a_5 = a_15 >> 1;
  c_6 = c_14 + 1;
  if (a_5 != 0)
goto ;
  else
goto ;

  :
  goto ;

  :
  # c_4 = PHI 
  stderr.0_1 = stderr;
  fprintf (stderr.0_1, "cnt: %d\n", c_4);
  return 0;
}

Diff:
  # a_15 = PHI 
  # a_15 = PHI <1(4), 3(2)>

Maybe ivcanon can handle such degenerated situation?
Thoughts?

[Bug tree-optimization/77975] [6/7 Regression] Missed optimization for some small constants

2016-10-13 Thread pinskia at gcc dot gnu.org
https://gcc.gnu.org/bugzilla/show_bug.cgi?id=77975

Andrew Pinski  changed:

   What|Removed |Added

   Keywords||missed-optimization
  Component|c   |tree-optimization
   Target Milestone|--- |6.3
Summary|[6 / 7 Regression] Missed   |[6/7 Regression] Missed
   |optimization for some small |optimization for some small
   |constants   |constants