pt.c (num_template_headers_for_class): Rework per the code inline in cp_parser_check_declarator_template_parameters.
2012-09-07 Paolo Carlini <paolo.carlini@oracle.com> * pt.c (num_template_headers_for_class): Rework per the code inline in cp_parser_check_declarator_template_parameters. * parser.c (cp_parser_check_declarator_template_parameters): Use num_template_headers_for_class. From-SVN: r191082
This commit is contained in:
parent
c294eb47b2
commit
e4394af568
|
@ -1,3 +1,10 @@
|
||||||
|
2012-09-07 Paolo Carlini <paolo.carlini@oracle.com>
|
||||||
|
|
||||||
|
* pt.c (num_template_headers_for_class): Rework per the code
|
||||||
|
inline in cp_parser_check_declarator_template_parameters.
|
||||||
|
* parser.c (cp_parser_check_declarator_template_parameters):
|
||||||
|
Use num_template_headers_for_class.
|
||||||
|
|
||||||
2012-09-06 Jason Merrill <jason@redhat.com>
|
2012-09-06 Jason Merrill <jason@redhat.com>
|
||||||
|
|
||||||
PR c++/54341
|
PR c++/54341
|
||||||
|
|
|
@ -20670,54 +20670,24 @@ cp_parser_check_declarator_template_parameters (cp_parser* parser,
|
||||||
cp_declarator *declarator,
|
cp_declarator *declarator,
|
||||||
location_t declarator_location)
|
location_t declarator_location)
|
||||||
{
|
{
|
||||||
unsigned num_templates;
|
|
||||||
|
|
||||||
/* We haven't seen any classes that involve template parameters yet. */
|
|
||||||
num_templates = 0;
|
|
||||||
|
|
||||||
switch (declarator->kind)
|
switch (declarator->kind)
|
||||||
{
|
{
|
||||||
case cdk_id:
|
case cdk_id:
|
||||||
if (declarator->u.id.qualifying_scope)
|
{
|
||||||
{
|
unsigned num_templates = 0;
|
||||||
tree scope;
|
tree scope = declarator->u.id.qualifying_scope;
|
||||||
|
|
||||||
scope = declarator->u.id.qualifying_scope;
|
if (scope)
|
||||||
|
num_templates = num_template_headers_for_class (scope);
|
||||||
while (scope && CLASS_TYPE_P (scope))
|
else if (TREE_CODE (declarator->u.id.unqualified_name)
|
||||||
{
|
== TEMPLATE_ID_EXPR)
|
||||||
/* You're supposed to have one `template <...>'
|
/* If the DECLARATOR has the form `X<y>' then it uses one
|
||||||
for every template class, but you don't need one
|
additional level of template parameters. */
|
||||||
for a full specialization. For example:
|
++num_templates;
|
||||||
|
|
||||||
template <class T> struct S{};
|
|
||||||
template <> struct S<int> { void f(); };
|
|
||||||
void S<int>::f () {}
|
|
||||||
|
|
||||||
is correct; there shouldn't be a `template <>' for
|
|
||||||
the definition of `S<int>::f'. */
|
|
||||||
if (!CLASSTYPE_TEMPLATE_INFO (scope))
|
|
||||||
/* If SCOPE does not have template information of any
|
|
||||||
kind, then it is not a template, nor is it nested
|
|
||||||
within a template. */
|
|
||||||
break;
|
|
||||||
if (explicit_class_specialization_p (scope))
|
|
||||||
break;
|
|
||||||
if (PRIMARY_TEMPLATE_P (CLASSTYPE_TI_TEMPLATE (scope)))
|
|
||||||
++num_templates;
|
|
||||||
|
|
||||||
scope = TYPE_CONTEXT (scope);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (TREE_CODE (declarator->u.id.unqualified_name)
|
|
||||||
== TEMPLATE_ID_EXPR)
|
|
||||||
/* If the DECLARATOR has the form `X<y>' then it uses one
|
|
||||||
additional level of template parameters. */
|
|
||||||
++num_templates;
|
|
||||||
|
|
||||||
return cp_parser_check_template_parameters
|
|
||||||
(parser, num_templates, declarator_location, declarator);
|
|
||||||
|
|
||||||
|
return cp_parser_check_template_parameters
|
||||||
|
(parser, num_templates, declarator_location, declarator);
|
||||||
|
}
|
||||||
|
|
||||||
case cdk_function:
|
case cdk_function:
|
||||||
case cdk_array:
|
case cdk_array:
|
||||||
|
|
27
gcc/cp/pt.c
27
gcc/cp/pt.c
|
@ -2214,9 +2214,9 @@ copy_default_args_to_explicit_spec (tree decl)
|
||||||
int
|
int
|
||||||
num_template_headers_for_class (tree ctype)
|
num_template_headers_for_class (tree ctype)
|
||||||
{
|
{
|
||||||
int template_count = 0;
|
int num_templates = 0;
|
||||||
tree t = ctype;
|
|
||||||
while (t != NULL_TREE && CLASS_TYPE_P (t))
|
while (ctype && CLASS_TYPE_P (ctype))
|
||||||
{
|
{
|
||||||
/* You're supposed to have one `template <...>' for every
|
/* You're supposed to have one `template <...>' for every
|
||||||
template class, but you don't need one for a full
|
template class, but you don't need one for a full
|
||||||
|
@ -2228,21 +2228,20 @@ num_template_headers_for_class (tree ctype)
|
||||||
|
|
||||||
is correct; there shouldn't be a `template <>' for the
|
is correct; there shouldn't be a `template <>' for the
|
||||||
definition of `S<int>::f'. */
|
definition of `S<int>::f'. */
|
||||||
if (CLASSTYPE_TEMPLATE_SPECIALIZATION (t)
|
if (!CLASSTYPE_TEMPLATE_INFO (ctype))
|
||||||
&& !any_dependent_template_arguments_p (CLASSTYPE_TI_ARGS (t)))
|
/* If CTYPE does not have template information of any
|
||||||
/* T is an explicit (not partial) specialization. All
|
kind, then it is not a template, nor is it nested
|
||||||
containing classes must therefore also be explicitly
|
within a template. */
|
||||||
specialized. */
|
|
||||||
break;
|
break;
|
||||||
if ((CLASSTYPE_USE_TEMPLATE (t) || CLASSTYPE_IS_TEMPLATE (t))
|
if (explicit_class_specialization_p (ctype))
|
||||||
&& PRIMARY_TEMPLATE_P (CLASSTYPE_TI_TEMPLATE (t)))
|
break;
|
||||||
template_count += 1;
|
if (PRIMARY_TEMPLATE_P (CLASSTYPE_TI_TEMPLATE (ctype)))
|
||||||
|
++num_templates;
|
||||||
|
|
||||||
t = TYPE_MAIN_DECL (t);
|
ctype = TYPE_CONTEXT (ctype);
|
||||||
t = DECL_CONTEXT (t);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return template_count;
|
return num_templates;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Do a simple sanity check on the template headers that precede the
|
/* Do a simple sanity check on the template headers that precede the
|
||||||
|
|
Loading…
Reference in New Issue