diff options
author | Jakub Jelinek <jakub@redhat.com> | 2013-02-08 15:06:26 +0000 |
---|---|---|
committer | Jakub Jelinek <jakub@redhat.com> | 2013-02-08 15:06:26 +0000 |
commit | 2f3befe400bcadacd0f5d9e44ff94e7d1d2c7b06 (patch) | |
tree | 3bef1543331fe45a7c674d160d1cafa5e1587232 /gcc/fold-const.c | |
parent | bb082ad5651c16aa531aea33be83c20912bbd7c1 (diff) |
PR tree-optimization/56250
* fold-const.c (extract_muldiv_1) <case NEGATE_EXPR>: Don't optimize
if type is unsigned and code isn't MULT_EXPR.
* gcc.c-torture/execute/pr56250.c: New test.
git-svn-id: https://gcc.gnu.org/svn/gcc/trunk@195888 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/fold-const.c')
-rw-r--r-- | gcc/fold-const.c | 5 |
1 files changed, 5 insertions, 0 deletions
diff --git a/gcc/fold-const.c b/gcc/fold-const.c index 93f38cbbf21..5acb4ad0059 100644 --- a/gcc/fold-const.c +++ b/gcc/fold-const.c @@ -5695,6 +5695,11 @@ extract_muldiv_1 (tree t, tree c, enum tree_code code, tree wide_type, break; /* FALLTHROUGH */ case NEGATE_EXPR: + /* For division and modulus, type can't be unsigned, as e.g. + (-(x / 2U)) / 2U isn't equal to -((x / 2U) / 2U) for x >= 2. + For signed types, even with wrapping overflow, this is fine. */ + if (code != MULT_EXPR && TYPE_UNSIGNED (type)) + break; if ((t1 = extract_muldiv (op0, c, code, wide_type, strict_overflow_p)) != 0) return fold_build1 (tcode, ctype, fold_convert (ctype, t1)); |