On Sat, 27 Apr 2013, Jakub Jelinek wrote: > Hi! > > If shift count range is [0, 1], then for unsigned LSHIFT_EXPR > bound is the topmost bit, but as llshift method always sign-extends > the result into double_int, the test don't properly find out that > deriving the value range is unsafe. In this case > vr0 is [0x7fff8001, 0x80000001], thus when shifting up by 0 or one bit > we might shift out either zero or 1. > > Fixed thusly, bootstrapped/regtested on x86_64-linux and i686-linux, ok for > trunk?
Ok. Thanks, Richard. > 2013-04-26 Jakub Jelinek <ja...@redhat.com> > > PR tree-optimization/57083 > * tree-vrp.c (extract_range_from_binary_expr_1): For LSHIFT_EXPR with > non-singleton shift count range, zero extend low_bound for uns case. > > * gcc.dg/torture/pr57083.c: New test. > > --- gcc/tree-vrp.c.jj 2013-04-24 12:07:07.000000000 +0200 > +++ gcc/tree-vrp.c 2013-04-26 17:59:41.077938198 +0200 > @@ -2837,7 +2837,7 @@ extract_range_from_binary_expr_1 (value_ > > if (uns) > { > - low_bound = bound; > + low_bound = bound.zext (prec); > high_bound = complement.zext (prec); > if (tree_to_double_int (vr0.max).ult (low_bound)) > { > --- gcc/testsuite/gcc.dg/torture/pr57083.c.jj 2013-04-26 18:09:05.396031875 > +0200 > +++ gcc/testsuite/gcc.dg/torture/pr57083.c 2013-04-26 18:08:51.000000000 > +0200 > @@ -0,0 +1,15 @@ > +/* PR tree-optimization/57083 */ > +/* { dg-do run { target int32plus } } */ > + > +extern void abort (void); > +short x = 1; > +int y = 0; > + > +int > +main () > +{ > + unsigned t = (0x7fff8001U - x) << (y == 0); > + if (t != 0xffff0000U) > + abort (); > + return 0; > +} > > Jakub > > -- Richard Biener <rguent...@suse.de> SUSE / SUSE Labs SUSE LINUX Products GmbH - Nuernberg - AG Nuernberg - HRB 16746 GF: Jeff Hawn, Jennifer Guild, Felix Imend