From 0229b692f4cba2d23b960284c79384b6f5b2309a Mon Sep 17 00:00:00 2001 From: Paolo Carlini Date: Mon, 16 Nov 2009 08:31:26 +0000 Subject: [PATCH] re PR c++/32056 (Storage classes on template parameters) cp/ 2009-11-16 Paolo Carlini PR c++/32056 * decl.h (enum decl_context): Add TPARM enumerator. * decl.c (grokdeclarator): Per 14.1/2, error out if a storage class is specified in a template parameter declaration. * parser.c (cp_parser_template_parameter): Call grokdeclarator with TPARM as third argument. testsuite/ 2009-11-16 Paolo Carlini PR c++/32056 * testsuite/g++.dg/template/error44.C: New. From-SVN: r154198 --- gcc/cp/ChangeLog | 9 +++++++++ gcc/cp/decl.c | 10 ++++++++++ gcc/cp/decl.h | 1 + gcc/cp/parser.c | 2 +- gcc/testsuite/ChangeLog | 5 +++++ gcc/testsuite/g++.dg/template/error44.C | 7 +++++++ 6 files changed, 33 insertions(+), 1 deletion(-) create mode 100644 gcc/testsuite/g++.dg/template/error44.C diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index d5dc053..2b18d01 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,12 @@ +2009-11-16 Paolo Carlini + + PR c++/32056 + * decl.h (enum decl_context): Add TPARM enumerator. + * decl.c (grokdeclarator): Per 14.1/2, error out if a storage class + is specified in a template parameter declaration. + * parser.c (cp_parser_template_parameter): Call grokdeclarator with + TPARM as third argument. + 2009-11-13 Jason Merrill PR c++/27425 diff --git a/gcc/cp/decl.c b/gcc/cp/decl.c index 0375dd5..73bf995 100644 --- a/gcc/cp/decl.c +++ b/gcc/cp/decl.c @@ -7574,11 +7574,13 @@ check_var_type (tree identifier, tree type) try to parse. PARM for a parameter declaration (either within a function prototype or before a function body). Make a PARM_DECL, or return void_type_node. + TPARM for a template parameter declaration. CATCHPARM for a parameter declaration before a catch clause. TYPENAME if for a typename (in a cast or sizeof). Don't make a DECL node; just return the ..._TYPE node. FIELD for a struct or union field; make a FIELD_DECL. BITFIELD for a field with specified width. + INITIALIZED is as for start_decl. ATTRLIST is a pointer to the list of attributes, which may be NULL @@ -7662,6 +7664,7 @@ grokdeclarator (const cp_declarator *declarator, bool type_was_error_mark_node = false; bool parameter_pack_p = declarator? declarator->parameter_pack_p : false; bool template_type_arg = false; + bool template_parm_flag = false; bool constexpr_p = declspecs->specs[(int) ds_constexpr]; const char *errmsg; @@ -7680,6 +7683,8 @@ grokdeclarator (const cp_declarator *declarator, bitfield = 1, decl_context = FIELD; else if (decl_context == TEMPLATE_TYPE_ARG) template_type_arg = true, decl_context = TYPENAME; + else if (decl_context == TPARM) + template_parm_flag = true, decl_context = PARM; if (initialized > 1) funcdef_flag = true; @@ -8179,6 +8184,11 @@ grokdeclarator (const cp_declarator *declarator, error ("typedef declaration invalid in parameter declaration"); return error_mark_node; } + else if (template_parm_flag && storage_class != sc_none) + { + error ("storage class specified for template parameter %qs", name); + return error_mark_node; + } else if (storage_class == sc_static || storage_class == sc_extern || thread_p) diff --git a/gcc/cp/decl.h b/gcc/cp/decl.h index d6e3c83..a8a2b78 100644 --- a/gcc/cp/decl.h +++ b/gcc/cp/decl.h @@ -23,6 +23,7 @@ enum decl_context { NORMAL, /* Ordinary declaration */ FUNCDEF, /* Function definition */ PARM, /* Declaration of parm before function body */ + TPARM, /* Declaration of template parm */ CATCHPARM, /* Declaration of catch parm */ FIELD, /* Declaration inside struct or union */ BITFIELD, /* Likewise but with specified width */ diff --git a/gcc/cp/parser.c b/gcc/cp/parser.c index 05def24..3a4b409 100644 --- a/gcc/cp/parser.c +++ b/gcc/cp/parser.c @@ -10508,7 +10508,7 @@ cp_parser_template_parameter (cp_parser* parser, bool *is_non_type, parm = grokdeclarator (parameter_declarator->declarator, ¶meter_declarator->decl_specifiers, - PARM, /*initialized=*/0, + TPARM, /*initialized=*/0, /*attrlist=*/NULL); if (parm == error_mark_node) return error_mark_node; diff --git a/gcc/testsuite/ChangeLog b/gcc/testsuite/ChangeLog index d685376..753a8b2 100644 --- a/gcc/testsuite/ChangeLog +++ b/gcc/testsuite/ChangeLog @@ -1,3 +1,8 @@ +2009-11-16 Paolo Carlini + + PR c++/32056 + * testsuite/g++.dg/template/error44.C: New. + 2009-11-16 Andreas Krebbel * gcc.c-torture/execute/pr41919.c: Mark chars explicitely as signed. diff --git a/gcc/testsuite/g++.dg/template/error44.C b/gcc/testsuite/g++.dg/template/error44.C new file mode 100644 index 0000000..4f732cd --- /dev/null +++ b/gcc/testsuite/g++.dg/template/error44.C @@ -0,0 +1,7 @@ +// PR c++/32056 + +template struct A {}; // { dg-error "storage class specified" } +template struct B {}; // { dg-error "storage class specified" } +template struct C {}; // { dg-error "storage class specified" } +template struct D {}; // { dg-error "storage class specified" } +template struct E {}; // { dg-error "storage class specified" } -- 2.7.4