On Tue, 7 Jan 2020, Jakub Jelinek wrote: > Hi! > > In x * x = ((x & -2) + (x & 1))^2 = ((x^2) & -4) + 2 * (x & -2) * (x & 1) + > (x & 1)^2 > the first two terms are divisible by 4 and the last one is 0 or 1, so > (x * x) % 4U <= 1 > and thus bit ccp can assume he second least significant bit of any power of > two is > 0. > > Bootstrapped/regtested on x86_64-linux and i686-linux, ok for trunk?
OK. Thanks, Richard. > 2020-01-07 Jakub Jelinek <ja...@redhat.com> > > PR tree-optimization/93156 > * tree-ssa-ccp.c (bit_value_binop): For x * x note that the second > least significant bit is always clear. > > * gcc.dg/tree-ssa/pr93156.c: New test. > > --- gcc/tree-ssa-ccp.c.jj 2020-01-01 12:15:48.026609558 +0100 > +++ gcc/tree-ssa-ccp.c 2020-01-06 15:39:16.807109578 +0100 > @@ -1650,6 +1650,17 @@ bit_value_binop (enum tree_code code, tr > TYPE_SIGN (TREE_TYPE (rhs2)), TYPE_PRECISION (TREE_TYPE > (rhs2)), > value_to_wide_int (r2val), r2val.mask); > > + /* (x * x) & 2 == 0. */ > + if (code == MULT_EXPR && rhs1 == rhs2 && TYPE_PRECISION (type) > 1) > + { > + widest_int m = 2; > + if (wi::sext (mask, TYPE_PRECISION (type)) != -1) > + value = wi::bit_and_not (value, m); > + else > + value = 0; > + mask = wi::bit_and_not (mask, m); > + } > + > if (wi::sext (mask, TYPE_PRECISION (type)) != -1) > { > val.lattice_val = CONSTANT; > --- gcc/testsuite/gcc.dg/tree-ssa/pr93156.c.jj 2020-01-06 > 15:26:57.750286597 +0100 > +++ gcc/testsuite/gcc.dg/tree-ssa/pr93156.c 2020-01-06 15:40:32.987957791 > +0100 > @@ -0,0 +1,23 @@ > +/* PR tree-optimization/93156 */ > +/* { dg-do compile } */ > +/* { dg-options "-O2 -fdump-tree-optimized" } */ > +/* { dg-final { scan-tree-dump-times "return 0;" 3 "optimized" } } */ > + > +int > +foo (int x) > +{ > + return (x * x) & 2; > +} > + > +unsigned long long > +bar (unsigned long long x) > +{ > + return (x * x) & 2; > +} > + > +int > +baz (int x) > +{ > + x &= -2; > + return (x * x) & 3; > +} > > Jakub > > -- Richard Biener <rguent...@suse.de> SUSE Software Solutions Germany GmbH, Maxfeldstrasse 5, 90409 Nuernberg, Germany; GF: Felix Imendörffer; HRB 36809 (AG Nuernberg)