diff options
author | James A. Morrison <phython@gcc.gnu.org> | 2005-10-01 13:57:29 +0000 |
---|---|---|
committer | Diego Novillo <dnovillo@gcc.gnu.org> | 2005-10-01 09:57:29 -0400 |
commit | fde5c44c5c8c5ea33da3cef11ad742309733dfb8 (patch) | |
tree | fce09b35d76668782499f03fb6d4aa8ccc08b2d7 /gcc/tree-vrp.c | |
parent | 0355186042ac451a8c12efd5296cf0c637d3094c (diff) | |
download | gcc-fde5c44c5c8c5ea33da3cef11ad742309733dfb8.zip gcc-fde5c44c5c8c5ea33da3cef11ad742309733dfb8.tar.gz gcc-fde5c44c5c8c5ea33da3cef11ad742309733dfb8.tar.bz2 |
re PR tree-optimization/23604 (wrong code due to VRP)
PR 23604
* tree-vrp.c (extract_range_from_assert): For !=
assertions, only build an anti-range if LIMIT is a
single-valued range.
testsuite/
PR 23604
* gcc.c-torture/execute/pr23604.c: New test.
Co-Authored-By: Diego Novillo <dnovillo@redhat.com>
From-SVN: r104858
Diffstat (limited to 'gcc/tree-vrp.c')
-rw-r--r-- | gcc/tree-vrp.c | 29 |
1 files changed, 22 insertions, 7 deletions
diff --git a/gcc/tree-vrp.c b/gcc/tree-vrp.c index 4aec9fc..21e6cf6 100644 --- a/gcc/tree-vrp.c +++ b/gcc/tree-vrp.c @@ -774,17 +774,32 @@ extract_range_from_assert (value_range_t *vr_p, tree expr) LIMIT's range was ~[0, 0], the assertion 'VAR != LIMIT' does not imply that VAR's range is [0, 0]. So, in the case of anti-ranges, we just assert the inequality using LIMIT and - not its anti-range. */ - if (limit_vr == NULL - || limit_vr->type == VR_ANTI_RANGE) + not its anti-range. + + If LIMIT_VR is a range, we can only use it to build a new + anti-range if LIMIT_VR is a single-valued range. For + instance, if LIMIT_VR is [0, 1], the predicate + VAR != [0, 1] does not mean that VAR's range is ~[0, 1]. + Rather, it means that for value 0 VAR should be ~[0, 0] + and for value 1, VAR should be ~[1, 1]. We cannot + represent these ranges. + + The only situation in which we can build a valid + anti-range is when LIMIT_VR is a single-valued range + (i.e., LIMIT_VR->MIN == LIMIT_VR->MAX). In that case, + build the anti-range ~[LIMIT_VR->MIN, LIMIT_VR->MAX]. */ + if (limit_vr + && limit_vr->type == VR_RANGE + && compare_values (limit_vr->min, limit_vr->max) == 0) { - min = limit; - max = limit; + min = limit_vr->min; + max = limit_vr->max; } else { - min = limit_vr->min; - max = limit_vr->max; + /* In any other case, we cannot use LIMIT's range to build a + valid anti-range. */ + min = max = limit; } /* If MIN and MAX cover the whole range for their type, then |