aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJakub Jelinek <jakub@redhat.com>2008-11-12 09:18:45 +0100
committerJakub Jelinek <jakub@gcc.gnu.org>2008-11-12 09:18:45 +0100
commit66e681911005962f96d56daf1a2b80bfe89cfbd2 (patch)
tree001e057e0e70c8a90aafba8c44da9fd2ef973064
parent8ebec1a5dd8a729cf24ad3cc708d9193392e8451 (diff)
downloadgcc-66e681911005962f96d56daf1a2b80bfe89cfbd2.zip
gcc-66e681911005962f96d56daf1a2b80bfe89cfbd2.tar.gz
gcc-66e681911005962f96d56daf1a2b80bfe89cfbd2.tar.bz2
re PR c++/35334 (Broken diagnostic for complex cast)
PR c++/35334 * c-pretty-print.c (pp_c_complex_expr): New function. (pp_c_postfix_expression) <case COMPLEX_EXPR>: Call it. * error.c (dump_expr): Handle COMPLEX_EXPR. * gcc.dg/pr35334.c: New test. * g++.dg/other/error29.C: New test. From-SVN: r141783
-rw-r--r--gcc/ChangeLog4
-rw-r--r--gcc/c-pretty-print.c45
-rw-r--r--gcc/cp/ChangeLog5
-rw-r--r--gcc/cp/error.c1
-rw-r--r--gcc/testsuite/ChangeLog6
-rw-r--r--gcc/testsuite/g++.dg/other/error29.C21
-rw-r--r--gcc/testsuite/gcc.dg/pr35334.c22
7 files changed, 103 insertions, 1 deletions
diff --git a/gcc/ChangeLog b/gcc/ChangeLog
index 6bb36f5..b8c38c1 100644
--- a/gcc/ChangeLog
+++ b/gcc/ChangeLog
@@ -1,5 +1,9 @@
2008-11-12 Jakub Jelinek <jakub@redhat.com>
+ PR c++/35334
+ * c-pretty-print.c (pp_c_complex_expr): New function.
+ (pp_c_postfix_expression) <case COMPLEX_EXPR>: Call it.
+
PR target/35366
* expr.c (expand_expr_addr_expr_1): If EXP needs bigger alignment
than INNER and INNER is a constant, forcibly align INNER as much
diff --git a/gcc/c-pretty-print.c b/gcc/c-pretty-print.c
index 67a466b..9ee2738 100644
--- a/gcc/c-pretty-print.c
+++ b/gcc/c-pretty-print.c
@@ -975,6 +975,46 @@ pp_c_compound_literal (c_pretty_printer *pp, tree e)
}
}
+/* Pretty-print a COMPLEX_EXPR expression. */
+
+static void
+pp_c_complex_expr (c_pretty_printer *pp, tree e)
+{
+ /* Handle a few common special cases, otherwise fallback
+ to printing it as compound literal. */
+ tree type = TREE_TYPE (e);
+ tree realexpr = TREE_OPERAND (e, 0);
+ tree imagexpr = TREE_OPERAND (e, 1);
+
+ /* Cast of an COMPLEX_TYPE expression to a different COMPLEX_TYPE. */
+ if (TREE_CODE (realexpr) == NOP_EXPR
+ && TREE_CODE (imagexpr) == NOP_EXPR
+ && TREE_TYPE (realexpr) == TREE_TYPE (type)
+ && TREE_TYPE (imagexpr) == TREE_TYPE (type)
+ && TREE_CODE (TREE_OPERAND (realexpr, 0)) == REALPART_EXPR
+ && TREE_CODE (TREE_OPERAND (imagexpr, 0)) == IMAGPART_EXPR
+ && TREE_OPERAND (TREE_OPERAND (realexpr, 0), 0)
+ == TREE_OPERAND (TREE_OPERAND (imagexpr, 0), 0))
+ {
+ pp_c_type_cast (pp, type);
+ pp_expression (pp, TREE_OPERAND (TREE_OPERAND (realexpr, 0), 0));
+ return;
+ }
+
+ /* Cast of an scalar expression to COMPLEX_TYPE. */
+ if ((integer_zerop (imagexpr) || real_zerop (imagexpr))
+ && TREE_TYPE (realexpr) == TREE_TYPE (type))
+ {
+ pp_c_type_cast (pp, type);
+ if (TREE_CODE (realexpr) == NOP_EXPR)
+ realexpr = TREE_OPERAND (realexpr, 0);
+ pp_expression (pp, realexpr);
+ return;
+ }
+
+ pp_c_compound_literal (pp, e);
+}
+
/* constant:
integer-constant
floating-constant
@@ -1406,10 +1446,13 @@ pp_c_postfix_expression (c_pretty_printer *pp, tree e)
case COMPLEX_CST:
case VECTOR_CST:
- case COMPLEX_EXPR:
pp_c_compound_literal (pp, e);
break;
+ case COMPLEX_EXPR:
+ pp_c_complex_expr (pp, e);
+ break;
+
case COMPOUND_LITERAL_EXPR:
e = DECL_INITIAL (COMPOUND_LITERAL_EXPR_DECL (e));
/* Fall through. */
diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog
index 81941e2..8cfdf61 100644
--- a/gcc/cp/ChangeLog
+++ b/gcc/cp/ChangeLog
@@ -1,3 +1,8 @@
+2008-11-12 Jakub Jelinek <jakub@redhat.com>
+
+ PR c++/35334
+ * error.c (dump_expr): Handle COMPLEX_EXPR.
+
2008-11-10 Jakub Jelinek <jakub@redhat.com>
PR c++/38021
diff --git a/gcc/cp/error.c b/gcc/cp/error.c
index 4064ad40..3aa9b59 100644
--- a/gcc/cp/error.c
+++ b/gcc/cp/error.c
@@ -2068,6 +2068,7 @@ dump_expr (tree t, int flags)
case UNGE_EXPR:
case UNEQ_EXPR:
case LTGT_EXPR:
+ case COMPLEX_EXPR:
pp_expression (cxx_pp, t);
break;
diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog
index df1cb86..922525f 100644
--- a/gcc/testsuite/ChangeLog
+++ b/gcc/testsuite/ChangeLog
@@ -1,3 +1,9 @@
+2008-11-12 Jakub Jelinek <jakub@redhat.com>
+
+ PR c++/35334
+ * gcc.dg/pr35334.c: New test.
+ * g++.dg/other/error29.C: New test.
+
2008-11-12 Tobias Burnus <burnus@net-b.de>
PR fortran/38065
diff --git a/gcc/testsuite/g++.dg/other/error29.C b/gcc/testsuite/g++.dg/other/error29.C
new file mode 100644
index 0000000..a464058
--- /dev/null
+++ b/gcc/testsuite/g++.dg/other/error29.C
@@ -0,0 +1,21 @@
+// PR c++/35334
+// { dg-do compile }
+// { dg-bogus "not supported by" "" { target *-*-* } 0 }
+
+__complex__ unsigned int i;
+int j;
+char k;
+__complex__ double l;
+double m;
+float n;
+
+void
+foo ()
+{
+ ((__complex__ int)i)(); // { dg-error "cannot be used as a function" }
+ ((__complex__ int)j)(); // { dg-error "cannot be used as a function" }
+ ((__complex__ int)k)(); // { dg-error "cannot be used as a function" }
+ ((__complex__ long double)l)(); // { dg-error "cannot be used as a function" }
+ ((__complex__ long double)m)(); // { dg-error "cannot be used as a function" }
+ ((__complex__ long double)n)(); // { dg-error "cannot be used as a function" }
+}
diff --git a/gcc/testsuite/gcc.dg/pr35334.c b/gcc/testsuite/gcc.dg/pr35334.c
new file mode 100644
index 0000000..d4c642e
--- /dev/null
+++ b/gcc/testsuite/gcc.dg/pr35334.c
@@ -0,0 +1,22 @@
+/* PR c++/35334 */
+/* { dg-do compile } */
+/* { dg-options "-std=gnu99" } */
+/* { dg-bogus "not supported by" "" { target *-*-* } 0 } */
+
+__complex__ unsigned int i;
+int j;
+char k;
+__complex__ double l;
+double m;
+float n;
+
+void
+foo ()
+{
+ ((__complex__ int)i)(); /* { dg-error "is not a function" } */
+ ((__complex__ int)j)(); /* { dg-error "is not a function" } */
+ ((__complex__ int)k)(); /* { dg-error "is not a function" } */
+ ((__complex__ long double)l)(); /* { dg-error "is not a function" } */
+ ((__complex__ long double)m)(); /* { dg-error "is not a function" } */
+ ((__complex__ long double)n)(); /* { dg-error "is not a function" } */
+}