re PR c++/51184 (Abstract class in function return type)

/cp
2012-05-21  Paolo Carlini  <paolo.carlini@oracle.com>

	PR c++/51184
	* decl.c (grokdeclarator): Diagnose functions returning abstract
	class types as TYPENAME.
	* cp-tree.h (ABSTRACT_CLASS_TYPE_P): Add.
	* except.c (is_admissible_throw_operand_or_catch_parameter): Use it.
	* pt.c (tsubst): Likewise.
	* semantics.c (trait_expr_value): Likewise.

/testsuite
2012-05-21  Paolo Carlini  <paolo.carlini@oracle.com>

	PR c++/51184
	* g++.dg/other/abstract4.C: New-

/cp
2012-05-21  Paolo Carlini  <paolo.carlini@oracle.com>

	PR c++/40821
	* parser.c (cp_parser_attributes_opt): Enforce error checking of
	unbalanced parentheses in the presence of tentative parsing.

/testsuite
2012-05-21  Paolo Carlini  <paolo.carlini@oracle.com>

	PR c++/40821
	* g++.dg/ext/attrib46.C: New.

From-SVN: r187720
This commit is contained in:
Paolo Carlini 2012-05-21 15:12:13 +00:00 committed by Paolo Carlini
parent cb0c9fc305
commit 94ccc95d41
10 changed files with 67 additions and 5 deletions

View File

@ -1,3 +1,19 @@
2012-05-21 Paolo Carlini <paolo.carlini@oracle.com>
PR c++/51184
* decl.c (grokdeclarator): Diagnose functions returning abstract
class types as TYPENAME.
* cp-tree.h (ABSTRACT_CLASS_TYPE_P): Add.
* except.c (is_admissible_throw_operand_or_catch_parameter): Use it.
* pt.c (tsubst): Likewise.
* semantics.c (trait_expr_value): Likewise.
2012-05-21 Paolo Carlini <paolo.carlini@oracle.com>
PR c++/40821
* parser.c (cp_parser_attributes_opt): Enforce error checking of
unbalanced parentheses in the presence of tentative parsing.
2012-05-17 Paolo Carlini <paolo.carlini@oracle.com>
PR c++/39681

View File

@ -1658,6 +1658,10 @@ struct GTY((variable_size)) lang_type {
#define CLASSTYPE_PURE_VIRTUALS(NODE) \
(LANG_TYPE_CLASS_CHECK (NODE)->pure_virtuals)
/* Nonzero means that this type is an abstract class type. */
#define ABSTRACT_CLASS_TYPE_P(NODE) \
(CLASS_TYPE_P (NODE) && CLASSTYPE_PURE_VIRTUALS(NODE))
/* Nonzero means that this type has an X() constructor. */
#define TYPE_HAS_DEFAULT_CONSTRUCTOR(NODE) \
(LANG_TYPE_CLASS_CHECK (NODE)->h.has_default_ctor)

View File

@ -9194,6 +9194,11 @@ grokdeclarator (const cp_declarator *declarator,
error ("%qs declared as function returning an array", name);
return error_mark_node;
}
/* When decl_context == NORMAL we emit a better error message
later in abstract_virtuals_error. */
if (decl_context == TYPENAME && ABSTRACT_CLASS_TYPE_P (type))
error ("%qs declared as function returning an abstract "
"class type", name);
/* Pick up type qualifiers which should be applied to `this'. */
memfn_quals = declarator->u.function.qualifiers;

View File

@ -974,7 +974,7 @@ is_admissible_throw_operand_or_catch_parameter (tree t, bool is_throw)
/* 10.4/3 An abstract class shall not be used as a parameter type,
as a function return type or as type of an explicit
conversion. */
else if (CLASS_TYPE_P (type) && CLASSTYPE_PURE_VIRTUALS (type))
else if (ABSTRACT_CLASS_TYPE_P (type))
{
if (is_throw)
error ("expression %qE of abstract class type %qT cannot "

View File

@ -20052,6 +20052,7 @@ cp_parser_attributes_opt (cp_parser* parser)
{
cp_token *token;
tree attribute_list;
bool ok = true;
/* Peek at the next token. */
token = cp_lexer_peek_token (parser->lexer);
@ -20076,8 +20077,12 @@ cp_parser_attributes_opt (cp_parser* parser)
attribute_list = NULL;
/* Look for the two `)' tokens. */
cp_parser_require (parser, CPP_CLOSE_PAREN, RT_CLOSE_PAREN);
cp_parser_require (parser, CPP_CLOSE_PAREN, RT_CLOSE_PAREN);
if (!cp_parser_require (parser, CPP_CLOSE_PAREN, RT_CLOSE_PAREN))
ok = false;
if (!cp_parser_require (parser, CPP_CLOSE_PAREN, RT_CLOSE_PAREN))
ok = false;
if (!ok)
cp_parser_skip_to_end_of_statement (parser);
/* Add these new attributes to the list. */
attributes = chainon (attributes, attribute_list);

View File

@ -11646,7 +11646,7 @@ tsubst (tree t, tree args, tsubst_flags_t complain, tree in_decl)
error ("creating array of %qT", type);
return error_mark_node;
}
if (CLASS_TYPE_P (type) && CLASSTYPE_PURE_VIRTUALS (type))
if (ABSTRACT_CLASS_TYPE_P (type))
{
if (complain & tf_error)
error ("creating array of %qT, which is an abstract class type",

View File

@ -5441,7 +5441,7 @@ trait_expr_value (cp_trait_kind kind, tree type1, tree type2)
return type_has_virtual_destructor (type1);
case CPTK_IS_ABSTRACT:
return (CLASS_TYPE_P (type1) && CLASSTYPE_PURE_VIRTUALS (type1));
return (ABSTRACT_CLASS_TYPE_P (type1));
case CPTK_IS_BASE_OF:
return (NON_UNION_CLASS_TYPE_P (type1) && NON_UNION_CLASS_TYPE_P (type2)

View File

@ -1,3 +1,13 @@
2012-05-21 Paolo Carlini <paolo.carlini@oracle.com>
PR c++/51184
* g++.dg/other/abstract4.C: New-
2012-05-21 Paolo Carlini <paolo.carlini@oracle.com>
PR c++/40821
* g++.dg/ext/attrib46.C: New.
2012-05-21 Joseph Myers <joseph@codesourcery.com>
PR c/53148

View File

@ -0,0 +1,4 @@
// PR c++/40821
struct __attribute__((aligned(8)) S1 { int i; }; // { dg-error "expected" }
struct __attribute__( aligned(8) S2 { int i; }; // { dg-error "expected" }

View File

@ -0,0 +1,18 @@
// PR c++/51184
template<typename T>
struct S { };
template<typename T>
void foo();
struct Abs
{
virtual void bar() = 0;
};
int main()
{
S<Abs(int)> s; // { dg-error "abstract" }
foo<Abs(int)>(); // { dg-error "abstract" }
}