summaryrefslogtreecommitdiff
path: root/gcc/tree-vrp.c
diff options
context:
space:
mode:
authorrguenth <rguenth@138bc75d-0d04-0410-961f-82ee72b054a4>2006-06-09 12:39:11 +0000
committerrguenth <rguenth@138bc75d-0d04-0410-961f-82ee72b054a4>2006-06-09 12:39:11 +0000
commit0086a3d6f91f6b6adecf17f1399939aeeacb2e37 (patch)
tree8f2366195492eca232eb1a6d8a000c1d7b4d5757 /gcc/tree-vrp.c
parentc8aa8448d8bcff74b6217d70fb9f60c0af32f317 (diff)
downloadgcc-0086a3d6f91f6b6adecf17f1399939aeeacb2e37.tar.gz
2006-06-09 Richard Guenther <rguenther@suse.de>
PR tree-optimization/26998 * tree-vrp.c (extract_range_from_unary_expr): For NEGATE_EXPR of signed types, only TYPE_MIN_VALUE is special, but for both, minimum and maximum value. Likewise VR_ANTI_RANGE is special in this case, as is -fwrapv. * gcc.dg/torture/pr26998.c: New testcase. * gcc.dg/tree-ssa/vrp29.c: New testcase. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@114507 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/tree-vrp.c')
-rw-r--r--gcc/tree-vrp.c23
1 files changed, 15 insertions, 8 deletions
diff --git a/gcc/tree-vrp.c b/gcc/tree-vrp.c
index 3ac01fb70f3..9eac7e9b67d 100644
--- a/gcc/tree-vrp.c
+++ b/gcc/tree-vrp.c
@@ -1795,14 +1795,21 @@ extract_range_from_unary_expr (value_range_t *vr, tree expr)
if (code == NEGATE_EXPR
&& !TYPE_UNSIGNED (TREE_TYPE (expr)))
{
- /* NEGATE_EXPR flips the range around. */
- min = (vr0.max == TYPE_MAX_VALUE (TREE_TYPE (expr)) && !flag_wrapv)
- ? TYPE_MIN_VALUE (TREE_TYPE (expr))
- : fold_unary_to_constant (code, TREE_TYPE (expr), vr0.max);
-
- max = (vr0.min == TYPE_MIN_VALUE (TREE_TYPE (expr)) && !flag_wrapv)
- ? TYPE_MAX_VALUE (TREE_TYPE (expr))
- : fold_unary_to_constant (code, TREE_TYPE (expr), vr0.min);
+ /* NEGATE_EXPR flips the range around. We need to treat
+ TYPE_MIN_VALUE specially dependent on wrapping, range type
+ and if it was used as minimum or maximum value:
+ -~[MIN, MIN] == ~[MIN, MIN]
+ -[MIN, 0] == [0, MAX] for -fno-wrapv
+ -[MIN, 0] == [0, MIN] for -fwrapv (will be set to varying later) */
+ min = vr0.max == TYPE_MIN_VALUE (TREE_TYPE (expr))
+ ? TYPE_MIN_VALUE (TREE_TYPE (expr))
+ : fold_unary_to_constant (code, TREE_TYPE (expr), vr0.max);
+
+ max = vr0.min == TYPE_MIN_VALUE (TREE_TYPE (expr))
+ ? (vr0.type == VR_ANTI_RANGE || flag_wrapv
+ ? TYPE_MIN_VALUE (TREE_TYPE (expr))
+ : TYPE_MAX_VALUE (TREE_TYPE (expr)))
+ : fold_unary_to_constant (code, TREE_TYPE (expr), vr0.min);
}
else if (code == NEGATE_EXPR