aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJakub Jelinek <jakub@redhat.com>2018-12-21 16:54:55 +0100
committerJakub Jelinek <jakub@gcc.gnu.org>2018-12-21 16:54:55 +0100
commitf9f248c8b86bbc5c69d4c3083d617736a65d7244 (patch)
treeb0383a5bf34aa046177c0201b4320f8670639d21
parent247c45b265ff85428aafb7cfcf6f968936ad48f3 (diff)
downloadgcc-f9f248c8b86bbc5c69d4c3083d617736a65d7244.zip
gcc-f9f248c8b86bbc5c69d4c3083d617736a65d7244.tar.gz
gcc-f9f248c8b86bbc5c69d4c3083d617736a65d7244.tar.bz2
re PR rtl-optimization/88563 (wrong code with -O2 -fno-code-hoisting -fno-tree-ccp -fno-tree-dominator-opts -fno-tree-forwprop -fno-tree-fre -fno-tree-pre -fno-tree-vrp)
PR rtl-optimization/88563 * expr.c (expand_expr_real_2) <case WIDEN_MULT_EXPR>: Swap innermode and mode arguments to convert_modes. Likewise swap mode and word_mode arguments. Handle both arguments with VOIDmode before convert_modes of one of them. Formatting fixes. * gcc.dg/pr88563.c: New test. From-SVN: r267326
-rw-r--r--gcc/ChangeLog8
-rw-r--r--gcc/expr.c24
-rw-r--r--gcc/testsuite/ChangeLog3
-rw-r--r--gcc/testsuite/gcc.dg/pr88563.c15
4 files changed, 37 insertions, 13 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index c7738e8..ce6ba2f 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,3 +1,11 @@
+2018-12-21 Jakub Jelinek <jakub@redhat.com>
+
+ PR rtl-optimization/88563
+ * expr.c (expand_expr_real_2) <case WIDEN_MULT_EXPR>: Swap innermode
+ and mode arguments to convert_modes. Likewise swap mode and word_mode
+ arguments. Handle both arguments with VOIDmode before convert_modes
+ of one of them. Formatting fixes.
+
2018-12-21 Uros Bizjak <ubizjak@gmail.com>
PR target/88556
diff --git a/gcc/expr.c b/gcc/expr.c
index fe3647f..8183134 100644
--- a/gcc/expr.c
+++ b/gcc/expr.c
@@ -8775,8 +8775,8 @@ expand_expr_real_2 (sepops ops, rtx target, machine_mode tmode,
!= INTEGER_CST check. Handle it. */
if (GET_MODE (op0) == VOIDmode && GET_MODE (op1) == VOIDmode)
{
- op0 = convert_modes (innermode, mode, op0, true);
- op1 = convert_modes (innermode, mode, op1, false);
+ op0 = convert_modes (mode, innermode, op0, true);
+ op1 = convert_modes (mode, innermode, op1, false);
return REDUCE_BIT_FIELD (expand_mult (mode, op0, op1,
target, unsignedp));
}
@@ -8798,7 +8798,7 @@ expand_expr_real_2 (sepops ops, rtx target, machine_mode tmode,
if (TREE_CODE (treeop0) != INTEGER_CST)
{
if (find_widening_optab_handler (this_optab, mode, innermode)
- != CODE_FOR_nothing)
+ != CODE_FOR_nothing)
{
expand_operands (treeop0, treeop1, NULL_RTX, &op0, &op1,
EXPAND_NORMAL);
@@ -8807,9 +8807,9 @@ expand_expr_real_2 (sepops ops, rtx target, machine_mode tmode,
if (GET_MODE (op0) == VOIDmode && GET_MODE (op1) == VOIDmode)
{
widen_mult_const:
- op0 = convert_modes (innermode, mode, op0, zextend_p);
+ op0 = convert_modes (mode, innermode, op0, zextend_p);
op1
- = convert_modes (innermode, mode, op1,
+ = convert_modes (mode, innermode, op1,
TYPE_UNSIGNED (TREE_TYPE (treeop1)));
return REDUCE_BIT_FIELD (expand_mult (mode, op0, op1,
target,
@@ -8820,21 +8820,19 @@ expand_expr_real_2 (sepops ops, rtx target, machine_mode tmode,
return REDUCE_BIT_FIELD (temp);
}
if (find_widening_optab_handler (other_optab, mode, innermode)
- != CODE_FOR_nothing
+ != CODE_FOR_nothing
&& innermode == word_mode)
{
rtx htem, hipart;
op0 = expand_normal (treeop0);
- if (TREE_CODE (treeop1) == INTEGER_CST)
- op1 = convert_modes (word_mode, mode,
- expand_normal (treeop1),
- TYPE_UNSIGNED (TREE_TYPE (treeop1)));
- else
- op1 = expand_normal (treeop1);
- /* op0 and op1 might still be constant, despite the above
+ op1 = expand_normal (treeop1);
+ /* op0 and op1 might be constants, despite the above
!= INTEGER_CST check. Handle it. */
if (GET_MODE (op0) == VOIDmode && GET_MODE (op1) == VOIDmode)
goto widen_mult_const;
+ if (TREE_CODE (treeop1) == INTEGER_CST)
+ op1 = convert_modes (mode, word_mode, op1,
+ TYPE_UNSIGNED (TREE_TYPE (treeop1)));
temp = expand_binop (mode, other_optab, op0, op1, target,
unsignedp, OPTAB_LIB_WIDEN);
hipart = gen_highpart (word_mode, temp);
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index 749a7b7..76ffd3d 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,5 +1,8 @@
2018-12-21 Jakub Jelinek <jakub@redhat.com>
+ PR rtl-optimization/88563
+ * gcc.dg/pr88563.c: New test.
+
PR c++/87125
* g++.dg/cpp0x/pr87125.C: New test.
diff --git a/gcc/testsuite/gcc.dg/pr88563.c b/gcc/testsuite/gcc.dg/pr88563.c
new file mode 100644
index 0000000..5526a8d
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr88563.c
@@ -0,0 +1,15 @@
+/* PR rtl-optimization/88563 */
+/* { dg-do run { target int128 } } */
+/* { dg-options "-O2 -fno-code-hoisting -fno-tree-ccp -fno-tree-dominator-opts -fno-tree-forwprop -fno-tree-fre -fno-tree-pre -fno-tree-vrp" } */
+
+int
+main ()
+{
+#if __SIZEOF_LONG_LONG__ == 8 && __SIZEOF_INT128__ == 16 && __CHAR_BIT__ == 8
+ unsigned __int128 a = 5;
+ __builtin_mul_overflow (0xffffffffffffffffULL, (unsigned long long) a, &a);
+ if (a != ((unsigned __int128)4 << 64 | 0xfffffffffffffffb))
+ __builtin_abort ();
+#endif
+ return 0;
+}