This is the mail archive of the gcc-patches@gcc.gnu.org mailing list for the GCC project.


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]
Other format: [Raw text]

[C PATCH] Avoid ICEs due to save_expr instead of c_save_expr (PR c/54428)


Hi!

This is another case of the issue that save_expr shouldn't be called
when parsing C (except for in_late_binary_op), but c_save_expr must be
called instead.

I wonder if we shouldn't add a langhook, which would do
if (in_late_binary_op) save_expr_1 else c_save_expr 
and ensure that when not parsing in_late_binary_op is set or something
similar, and if non-NULL, call the langhook from save_expr.

Anyway, this patch fixes this issue even without such changes,
bootstrapped/regtested on x86_64-linux and i686-linux, ok for trunk/4.7?

2012-08-31  Jakub Jelinek  <jakub@redhat.com>

	PR c/54428
	* c-convert.c (convert): Don't call fold_convert_loc if
	TYPE_MAIN_VARIANT of a COMPLEX_TYPE is the same, unless e
	is a COMPLEX_EXPR.  Remove TYPE_MAIN_VARIANT check from
	COMPLEX_TYPE -> COMPLEX_TYPE conversion.

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

--- gcc/c/c-convert.c.jj	2012-06-29 21:22:02.000000000 +0200
+++ gcc/c/c-convert.c	2012-08-31 10:25:55.265821242 +0200
@@ -1,6 +1,6 @@
 /* Language-level data type conversion for GNU C.
    Copyright (C) 1987, 1988, 1991, 1998, 2002, 2003, 2004, 2005, 2007, 2008,
-   2009, 2010 Free Software Foundation, Inc.
+   2009, 2010, 2011, 2012 Free Software Foundation, Inc.
 
 This file is part of GCC.
 
@@ -92,7 +92,9 @@ convert (tree type, tree expr)
 
   STRIP_TYPE_NOPS (e);
 
-  if (TYPE_MAIN_VARIANT (type) == TYPE_MAIN_VARIANT (TREE_TYPE (expr)))
+  if (TYPE_MAIN_VARIANT (type) == TYPE_MAIN_VARIANT (TREE_TYPE (expr))
+      && (TREE_CODE (TREE_TYPE (expr)) != COMPLEX_TYPE
+	  || TREE_CODE (e) == COMPLEX_EXPR))
     return fold_convert_loc (loc, type, expr);
   if (TREE_CODE (TREE_TYPE (expr)) == ERROR_MARK)
     return error_mark_node;
@@ -135,24 +137,23 @@ convert (tree type, tree expr)
 	 but for the C FE c_save_expr needs to be called instead.  */
       if (TREE_CODE (TREE_TYPE (e)) == COMPLEX_TYPE)
 	{
-	  tree subtype = TREE_TYPE (type);
-	  tree elt_type = TREE_TYPE (TREE_TYPE (e));
-
-	  if (TYPE_MAIN_VARIANT (elt_type) != TYPE_MAIN_VARIANT (subtype)
-	      && TREE_CODE (e) != COMPLEX_EXPR)
+	  if (TREE_CODE (e) != COMPLEX_EXPR)
 	    {
+	      tree subtype = TREE_TYPE (type);
+	      tree elt_type = TREE_TYPE (TREE_TYPE (e));
+
 	      if (in_late_binary_op)
 		e = save_expr (e);
 	      else
 		e = c_save_expr (e);
 	      ret
-		= fold_build2 (COMPLEX_EXPR, type,
-			       convert (subtype,
-					fold_build1 (REALPART_EXPR,
-						     elt_type, e)),
-			       convert (subtype,
-					fold_build1 (IMAGPART_EXPR,
-						     elt_type, e)));
+		= fold_build2_loc (loc, COMPLEX_EXPR, type,
+				   convert (subtype,
+					    fold_build1 (REALPART_EXPR,
+							 elt_type, e)),
+				   convert (subtype,
+					    fold_build1 (IMAGPART_EXPR,
+							 elt_type, e)));
 	      goto maybe_fold;
 	    }
 	}
--- gcc/testsuite/gcc.c-torture/compile/pr54428.c.jj	2012-08-31 10:27:51.941225923 +0200
+++ gcc/testsuite/gcc.c-torture/compile/pr54428.c	2012-08-31 10:27:09.000000000 +0200
@@ -0,0 +1,9 @@
+/* PR c/54428 */
+
+typedef double _Complex C;
+
+C
+foo (C x, C y, double z, C w)
+{
+  return y - z * __builtin_cpow (x, 75) * w;
+}

	Jakub


Index Nav: [Date Index] [Subject Index] [Author Index] [Thread Index]
Message Nav: [Date Prev] [Date Next] [Thread Prev] [Thread Next]