From 711178fb7998b8914bd809410c4caf59f72ad2f1 Mon Sep 17 00:00:00 2001 From: jakub Date: Thu, 29 Nov 2007 21:04:04 +0000 Subject: [PATCH] PR c++/34267 PR c++/34268 * parser.c (cp_parser_decltype): Don't call finish_id_expression on ~type. * semantics.c (finish_decltype_type): Issue error on types, TYPE_DECLs and ~type early. * g++.dg/cpp0x/decltype7.C: New test. * g++.dg/cpp0x/decltype8.C: New test. git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@130519 138bc75d-0d04-0410-961f-82ee72b054a4 --- gcc/cp/ChangeLog | 9 +++++++++ gcc/cp/parser.c | 4 +++- gcc/cp/semantics.c | 9 +++++++++ gcc/testsuite/ChangeLog | 7 +++++++ gcc/testsuite/g++.dg/cpp0x/decltype7.C | 14 ++++++++++++++ gcc/testsuite/g++.dg/cpp0x/decltype8.C | 12 ++++++++++++ 6 files changed, 54 insertions(+), 1 deletion(-) create mode 100644 gcc/testsuite/g++.dg/cpp0x/decltype7.C create mode 100644 gcc/testsuite/g++.dg/cpp0x/decltype8.C diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index ea87688..3f7f9dc 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,12 @@ +2007-11-29 Jakub Jelinek + + PR c++/34267 + PR c++/34268 + * parser.c (cp_parser_decltype): Don't call finish_id_expression + on ~type. + * semantics.c (finish_decltype_type): Issue error on types, TYPE_DECLs + and ~type early. + 2007-11-27 Jakub Jelinek PR tree-optimization/34181 diff --git a/gcc/cp/parser.c b/gcc/cp/parser.c index 8e16d22..7b173f0 100644 --- a/gcc/cp/parser.c +++ b/gcc/cp/parser.c @@ -8512,10 +8512,12 @@ cp_parser_decltype (cp_parser *parser) /*check_dependency=*/true, /*ambiguous_decls=*/NULL); - if (expr + if (expr && expr != error_mark_node && TREE_CODE (expr) != TEMPLATE_ID_EXPR && TREE_CODE (expr) != TYPE_DECL + && (TREE_CODE (expr) != BIT_NOT_EXPR + || !TYPE_P (TREE_OPERAND (expr, 0))) && cp_lexer_peek_token (parser->lexer)->type == CPP_CLOSE_PAREN) { /* Complete lookup of the id-expression. */ diff --git a/gcc/cp/semantics.c b/gcc/cp/semantics.c index 1ae7d0f..381774e 100644 --- a/gcc/cp/semantics.c +++ b/gcc/cp/semantics.c @@ -4066,6 +4066,15 @@ finish_decltype_type (tree expr, bool id_expression_or_member_access_p) if (!expr || error_operand_p (expr)) return error_mark_node; + if (TYPE_P (expr) + || TREE_CODE (expr) == TYPE_DECL + || (TREE_CODE (expr) == BIT_NOT_EXPR + && TYPE_P (TREE_OPERAND (expr, 0)))) + { + error ("argument to decltype must be an expression"); + return error_mark_node; + } + if (type_dependent_expression_p (expr)) { type = make_aggr_type (DECLTYPE_TYPE); diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index 889d220..c04a77f 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,10 @@ +2007-11-29 Jakub Jelinek + + PR c++/34267 + PR c++/34268 + * g++.dg/cpp0x/decltype7.C: New test. + * g++.dg/cpp0x/decltype8.C: New test. + 2007-11-29 Tobias Burnus PR fortran/34248 diff --git a/gcc/testsuite/g++.dg/cpp0x/decltype7.C b/gcc/testsuite/g++.dg/cpp0x/decltype7.C new file mode 100644 index 0000000..f757c9e --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/decltype7.C @@ -0,0 +1,14 @@ +// PR c++/34268 +// { dg-do compile } + +struct A +{ + __decltype (A); // { dg-error "must be an expression" } + __decltype (~A); // { dg-error "must be an expression" } +}; + +struct B +{ + __typeof__ (B); + __typeof__ (~B); // { dg-error "expected primary-expression" } +}; diff --git a/gcc/testsuite/g++.dg/cpp0x/decltype8.C b/gcc/testsuite/g++.dg/cpp0x/decltype8.C new file mode 100644 index 0000000..3680689 --- /dev/null +++ b/gcc/testsuite/g++.dg/cpp0x/decltype8.C @@ -0,0 +1,12 @@ +// PR c++/34267 +// { dg-do compile } + +struct A {}; +__decltype (A); // { dg-error "must be an expression" } +template struct B +{ + __decltype (A); // { dg-error "must be an expression" } + __decltype (~A); // { dg-error "must be an expression" } + __decltype (B); // { dg-error "must be an expression" } + __decltype (~B); // { dg-error "must be an expression" } +}; -- 2.7.4