Hi!

unsigned_type_for doesn't handle complex types, so will return NULL for
them, which this optimization wasn't prepared to handle.

Fixed thusly, bootstrapped/regtested on x86_64-linux and i686-linux,
pre-approved in the PR by Richard, committed to trunk and will commit to
8.2.

This doesn't mean we can't change on the trunk {,un}signed_type_for to handle
complex types, I just don't have cycles to handle it now.

2018-06-14  Jakub Jelinek  <ja...@redhat.com>

        PR middle-end/86122
        * match.pd ((A +- CST1) +- CST2): Punt if last resort
        unsigned_type_for returns NULL.

        * gcc.c-torture/compile/pr86122.c: New test.

--- gcc/match.pd.jj     2018-05-25 14:34:42.268381974 +0200
+++ gcc/match.pd        2018-06-14 15:53:20.538712014 +0200
@@ -1771,10 +1771,11 @@ (define_operator_list COND_BINARY
           (neg_inner_op @0 { wide_int_to_tree (type, wi::to_wide (cst)); })
           /* Last resort, use some unsigned type.  */
           (with { tree utype = unsigned_type_for (type); }
-           (view_convert (inner_op
-                          (view_convert:utype @0)
-                          (view_convert:utype
-                           { drop_tree_overflow (cst); })))))))))))))
+           (if (utype)
+            (view_convert (inner_op
+                           (view_convert:utype @0)
+                           (view_convert:utype
+                            { drop_tree_overflow (cst); }))))))))))))))
 
   /* (CST1 - A) +- CST2 -> CST3 - A  */
   (for outer_op (plus minus)
--- gcc/testsuite/gcc.c-torture/compile/pr86122.c.jj    2018-06-14 
15:58:14.676891695 +0200
+++ gcc/testsuite/gcc.c-torture/compile/pr86122.c       2018-06-14 
15:58:27.557899555 +0200
@@ -0,0 +1,17 @@
+/* PR middle-end/86122 */
+
+_Complex int
+foo (_Complex int x)
+{
+  x += __INT_MAX__;
+  x += 1;
+  return x;
+}
+
+_Complex int
+bar (_Complex int x)
+{
+  x += 1;
+  x += __INT_MAX__;
+  return x;
+}

        Jakub

Reply via email to