diff options
author | Jason Merrill <jason@redhat.com> | 2009-03-31 14:31:17 -0400 |
---|---|---|
committer | Jason Merrill <jason@gcc.gnu.org> | 2009-03-31 14:31:17 -0400 |
commit | 0d9c089222329e55fb3d372e3c8029f5a18a080f (patch) | |
tree | 155b10aa3c254e87c8ef3b1be4137739cf355dfb /gcc/cp/decl.c | |
parent | a3c497526740202a565d78c77d29f2b93c92f1ee (diff) | |
download | gcc-0d9c089222329e55fb3d372e3c8029f5a18a080f.zip gcc-0d9c089222329e55fb3d372e3c8029f5a18a080f.tar.gz gcc-0d9c089222329e55fb3d372e3c8029f5a18a080f.tar.bz2 |
re PR c++/37806 (CV-qualifiers on function typedef's are inconsistently accepted depending on typedef scope)
PR c++/37806
* typeck.c (cp_apply_type_quals_to_decl): Don't apply any quals
to a typedef.
* tree.c (cp_build_qualified_type_real): Don't apply restrict to a
function type.
* decl.h (enum decl_context): Add TEMPLATE_TYPE_ARG.
* decl.c (groktypename): Add is_template_arg parameter.
(grokdeclarator): Allow function cv-quals on a template type arg.
* parser.c (cp_parser_new_type_id, cp_parser_type_id): Add
is_template_arg argument in calls to groktypename.
* cp-tree.h: Adjust prototype.
* error.c (dump_type_prefix, dump_type_suffix): Fix plain
FUNCTION_TYPE printing.
PR libstdc++/39310
* include/tr1_impl/type_traits (is_function): Add partial
specializations with function cv-quals.
(__is_function_helper): Remove.
(is_member_pointer): Don't define in terms of is_member_*_pointer.
From-SVN: r145365
Diffstat (limited to 'gcc/cp/decl.c')
-rw-r--r-- | gcc/cp/decl.c | 32 |
1 files changed, 23 insertions, 9 deletions
diff --git a/gcc/cp/decl.c b/gcc/cp/decl.c index b16ae26..6537c50 100644 --- a/gcc/cp/decl.c +++ b/gcc/cp/decl.c @@ -3967,13 +3967,16 @@ shadow_tag (cp_decl_specifier_seq *declspecs) tree groktypename (cp_decl_specifier_seq *type_specifiers, - const cp_declarator *declarator) + const cp_declarator *declarator, + bool is_template_arg) { tree attrs; tree type; + enum decl_context context + = is_template_arg ? TEMPLATE_TYPE_ARG : TYPENAME; attrs = type_specifiers->attributes; type_specifiers->attributes = NULL_TREE; - type = grokdeclarator (declarator, type_specifiers, TYPENAME, 0, &attrs); + type = grokdeclarator (declarator, type_specifiers, context, 0, &attrs); if (attrs && type != error_mark_node) { if (CLASS_TYPE_P (type)) @@ -7603,6 +7606,7 @@ grokdeclarator (const cp_declarator *declarator, bool type_was_error_mark_node = false; bool parameter_pack_p = declarator? declarator->parameter_pack_p : false; bool set_no_warning = false; + bool template_type_arg = false; signed_p = declspecs->specs[(int)ds_signed]; unsigned_p = declspecs->specs[(int)ds_unsigned]; @@ -7617,6 +7621,8 @@ grokdeclarator (const cp_declarator *declarator, funcdef_flag = true, decl_context = FIELD; else if (decl_context == BITFIELD) bitfield = 1, decl_context = FIELD; + else if (decl_context == TEMPLATE_TYPE_ARG) + template_type_arg = true, decl_context = TYPENAME; if (initialized > 1) funcdef_flag = true; @@ -8476,6 +8482,12 @@ grokdeclarator (const cp_declarator *declarator, memfn_quals = TYPE_UNQUALIFIED; } + if (TREE_CODE (type) == FUNCTION_TYPE + && cp_type_quals (type) != TYPE_UNQUALIFIED) + error ("cannot declare %s to qualified function type %qT", + declarator->kind == cdk_reference ? "reference" : "pointer", + type); + if (declarator->kind == cdk_reference) { /* In C++0x, the type we are creating a reference to might be @@ -8948,15 +8960,17 @@ grokdeclarator (const cp_declarator *declarator, } else if (memfn_quals) { - if (ctype == NULL_TREE) - { - if (TREE_CODE (type) != METHOD_TYPE) - error ("invalid qualifiers on non-member function type"); - else - ctype = TYPE_METHOD_BASETYPE (type); - } + if (ctype == NULL_TREE + && TREE_CODE (type) == METHOD_TYPE) + ctype = TYPE_METHOD_BASETYPE (type); + if (ctype) type = build_memfn_type (type, ctype, memfn_quals); + /* Core issue #547: need to allow this in template type args. */ + else if (template_type_arg && TREE_CODE (type) == FUNCTION_TYPE) + type = cp_build_qualified_type (type, memfn_quals); + else + error ("invalid qualifiers on non-member function type"); } return type; |