+2005-09-06 Volker Reichelt <reichelt@igpm.rwth-aachen.de>
+
+ Backport:
+
+ 2004-12-14 Mark Mitchell <mark@codesourcery.com>
+ PR c++/18738
+ * decl.c (make_typename_type): Do not handle namespace-scoped
+ names here.
+ (tag_name): Handle typename_type.
+ (check_elaborated_type_specifier): Handle typenames.
+ * parser.c (cp_parser_diagnose_invalid_type_name): Do not call
+ make_typename_type for namespace-scoped names here.
+ (cp_parser_elaborated_type_specifier): Use
+ cp_parser_diagnose_invalid_type_name.
+
2005-09-03 Volker Reichelt <reichelt@igpm.rwth-aachen.de>
Backport:
return error_mark_node;
}
my_friendly_assert (TREE_CODE (name) == IDENTIFIER_NODE, 20030802);
-
- if (TREE_CODE (context) == NAMESPACE_DECL)
- {
- /* We can get here from typename_sub0 in the explicit_template_type
- expansion. Just fail. */
- if (complain & tf_error)
- error ("no class template named `%#T' in `%#T'",
- name, context);
- return error_mark_node;
- }
+ my_friendly_assert (TYPE_P (context), 20050905);
if (!dependent_type_p (context)
|| currently_open_class (context))
case class_type:
return "class";
case union_type:
- return "union ";
+ return "union";
case enum_type:
return "enum";
+ case typename_type:
+ return "typename";
default:
abort ();
}
In other words, the only legitimate declaration to use in the
elaborated type specifier is the implicit typedef created when
the type is declared. */
- if (!DECL_IMPLICIT_TYPEDEF_P (decl))
+ if (!DECL_IMPLICIT_TYPEDEF_P (decl)
+ && tag_code != typename_type)
{
error ("using typedef-name `%D' after `%s'", decl, tag_name (tag_code));
return IS_AGGR_TYPE (type) ? type : error_mark_node;
}
else if (TREE_CODE (type) != RECORD_TYPE
&& TREE_CODE (type) != UNION_TYPE
- && tag_code != enum_type)
+ && tag_code != enum_type
+ && tag_code != typename_type)
{
error ("`%T' referred to as `%s'", type, tag_name (tag_code));
return error_mark_node;
}
/* For a `typename', we needn't call xref_tag. */
- if (tag_type == typename_type)
+ if (tag_type == typename_type
+ && TREE_CODE (parser->scope) != NAMESPACE_DECL)
return make_typename_type (parser->scope, identifier,
/*complain=*/1);
/* Look up a qualified name in the usual way. */
if (TREE_CODE (decl) != TYPE_DECL)
{
- error ("expected type-name");
+ cp_parser_diagnose_invalid_type_name (parser);
return error_mark_node;
}
+2005-09-06 Volker Reichelt <reichelt@igpm.rwth-aachen.de>
+
+ Backport:
+
+ 2004-12-14 Mark Mitchell <mark@codesourcery.com>
+ PR c++/18738
+ * g++.dg/template/typename8.C: New test.
+ * g++.dg/parse/friend2.C: Tweak error message.
+
2005-09-03 Volker Reichelt <reichelt@igpm.rwth-aachen.de>
Backport: