Commit 85b71cf2 by Jason Merrill

[multiple changes]

Thu Sep 11 17:14:55 1997  Jason Merrill  <jason@yorick.cygnus.com>

	* decl.c (lookup_name_real): Add implicit 'typename' to types from
	base classes.

	* pt.c (most_specialized_class): Fix typo.
	(tsubst): Move constant folding to TREE_VEC case.

Thu Sep 11 10:08:45 1997  Mark Mitchell  <mmitchell@usa.net>

	* pt.c (do_poplevel): Don't warn about unused local variables
	while processing_template_decl since we don't always know whether
	or not they will need constructing/destructing.

	* pt.c (uses_template_parms): Check the values of an enumeration
	type to make sure they don't depend on template parms.

	* decl.c (make_typename_type): Don't lookup the field if the
	context uses template parms, even if we're not
	processing_template_decl at the moment.

	* pt.c (coerce_template_parms): Avoid looking at the
	TYPE_LANG_DECL portion of a typename type, since there won't be
	one.
	(tsubst): Do constant folding as necessary to make sure that
	arguments passed to lookup_template_class really are constants.

From-SVN: r15422
parent 5188d2b2
Thu Sep 11 17:14:55 1997 Jason Merrill <jason@yorick.cygnus.com>
* decl.c (lookup_name_real): Add implicit 'typename' to types from
base classes.
* pt.c (most_specialized_class): Fix typo.
(tsubst): Move constant folding to TREE_VEC case.
Thu Sep 11 10:08:45 1997 Mark Mitchell <mmitchell@usa.net>
* pt.c (do_poplevel): Don't warn about unused local variables
while processing_template_decl since we don't always know whether
or not they will need constructing/destructing.
* pt.c (uses_template_parms): Check the values of an enumeration
type to make sure they don't depend on template parms.
* decl.c (make_typename_type): Don't lookup the field if the
context uses template parms, even if we're not
processing_template_decl at the moment.
* pt.c (coerce_template_parms): Avoid looking at the
TYPE_LANG_DECL portion of a typename type, since there won't be
one.
(tsubst): Do constant folding as necessary to make sure that
arguments passed to lookup_template_class really are constants.
Tue Sep 9 19:49:38 1997 Jason Merrill <jason@yorick.cygnus.com> Tue Sep 9 19:49:38 1997 Jason Merrill <jason@yorick.cygnus.com>
* pt.c (unify): Just return 0 for a TYPENAME_TYPE. * pt.c (unify): Just return 0 for a TYPENAME_TYPE.
......
...@@ -4322,8 +4322,7 @@ make_typename_type (context, name) ...@@ -4322,8 +4322,7 @@ make_typename_type (context, name)
else if (TREE_CODE (name) != IDENTIFIER_NODE) else if (TREE_CODE (name) != IDENTIFIER_NODE)
my_friendly_abort (2000); my_friendly_abort (2000);
if (! processing_template_decl if (! uses_template_parms (context)
|| ! uses_template_parms (context)
|| context == current_class_type) || context == current_class_type)
{ {
t = lookup_field (context, name, 0, 1); t = lookup_field (context, name, 0, 1);
...@@ -4432,7 +4431,7 @@ lookup_name_real (name, prefer_type, nonclass) ...@@ -4432,7 +4431,7 @@ lookup_name_real (name, prefer_type, nonclass)
else else
val = NULL_TREE; val = NULL_TREE;
#if 1 /* Add implicit 'typename' to scoped types from other classes. */
if (got_scope && processing_template_decl if (got_scope && processing_template_decl
&& got_scope != current_class_type && got_scope != current_class_type
&& uses_template_parms (got_scope) && uses_template_parms (got_scope)
...@@ -4443,7 +4442,6 @@ lookup_name_real (name, prefer_type, nonclass) ...@@ -4443,7 +4442,6 @@ lookup_name_real (name, prefer_type, nonclass)
TREE_TYPE (t) = TREE_TYPE (val); TREE_TYPE (t) = TREE_TYPE (val);
val = TYPE_MAIN_DECL (t); val = TYPE_MAIN_DECL (t);
} }
#endif
if (got_scope) if (got_scope)
goto done; goto done;
...@@ -4473,6 +4471,19 @@ lookup_name_real (name, prefer_type, nonclass) ...@@ -4473,6 +4471,19 @@ lookup_name_real (name, prefer_type, nonclass)
created the COMPONENT_REF or anything like that. */ created the COMPONENT_REF or anything like that. */
if (classval == NULL_TREE) if (classval == NULL_TREE)
classval = lookup_nested_field (name, ! yylex); classval = lookup_nested_field (name, ! yylex);
/* Add implicit 'typename' to types from base classes. */
if (processing_template_decl
&& classval && TREE_CODE (classval) == TYPE_DECL
&& DECL_CONTEXT (classval) != current_class_type
&& uses_template_parms (DECL_CONTEXT (classval))
&& ! DECL_ARTIFICIAL (classval))
{
tree t = make_typename_type (DECL_CONTEXT (classval),
DECL_NAME (classval));
TREE_TYPE (t) = TREE_TYPE (classval);
classval = TYPE_MAIN_DECL (t);
}
} }
if (locval && classval) if (locval && classval)
......
...@@ -658,7 +658,8 @@ coerce_template_parms (parms, arglist, in_decl) ...@@ -658,7 +658,8 @@ coerce_template_parms (parms, arglist, in_decl)
if (! processing_template_decl) if (! processing_template_decl)
{ {
tree t = target_type (val); tree t = target_type (val);
if (IS_AGGR_TYPE (t) if (TREE_CODE (t) != TYPENAME_TYPE
&& IS_AGGR_TYPE (t)
&& decl_function_context (TYPE_MAIN_DECL (t))) && decl_function_context (TYPE_MAIN_DECL (t)))
{ {
cp_error ("type `%T' composed from a local class is not a valid template-argument", val); cp_error ("type `%T' composed from a local class is not a valid template-argument", val);
...@@ -1146,10 +1147,19 @@ uses_template_parms (t) ...@@ -1146,10 +1147,19 @@ uses_template_parms (t)
case REAL_TYPE: case REAL_TYPE:
case COMPLEX_TYPE: case COMPLEX_TYPE:
case VOID_TYPE: case VOID_TYPE:
case ENUMERAL_TYPE:
case BOOLEAN_TYPE: case BOOLEAN_TYPE:
return 0; return 0;
case ENUMERAL_TYPE:
{
tree v;
for (v = TYPE_VALUES (t); v != NULL_TREE; v = TREE_CHAIN (v))
if (uses_template_parms (TREE_VALUE (v)))
return 1;
}
return 0;
/* constants */ /* constants */
case INTEGER_CST: case INTEGER_CST:
case REAL_CST: case REAL_CST:
...@@ -2084,6 +2094,8 @@ tsubst (t, args, nargs, in_decl) ...@@ -2084,6 +2094,8 @@ tsubst (t, args, nargs, in_decl)
case TREE_VEC: case TREE_VEC:
if (type != NULL_TREE) if (type != NULL_TREE)
{ {
/* A binfo node. */
t = copy_node (t); t = copy_node (t);
if (type == TREE_TYPE (t)) if (type == TREE_TYPE (t))
...@@ -2099,6 +2111,8 @@ tsubst (t, args, nargs, in_decl) ...@@ -2099,6 +2111,8 @@ tsubst (t, args, nargs, in_decl)
} }
return t; return t;
} }
/* Otherwise, a vector of template arguments. */
{ {
int len = TREE_VEC_LENGTH (t), need_new = 0, i; int len = TREE_VEC_LENGTH (t), need_new = 0, i;
tree *elts = (tree *) alloca (len * sizeof (tree)); tree *elts = (tree *) alloca (len * sizeof (tree));
...@@ -2108,6 +2122,24 @@ tsubst (t, args, nargs, in_decl) ...@@ -2108,6 +2122,24 @@ tsubst (t, args, nargs, in_decl)
for (i = 0; i < len; i++) for (i = 0; i < len; i++)
{ {
elts[i] = tsubst_expr (TREE_VEC_ELT (t, i), args, nargs, in_decl); elts[i] = tsubst_expr (TREE_VEC_ELT (t, i), args, nargs, in_decl);
if (TREE_CODE_CLASS (TREE_CODE (elts[i])) != 't'
&& !uses_template_parms (elts[i]))
{
/* Sometimes, one of the args was an expression involving a
template constant parameter, like N - 1. Now that we've
tsubst'd, we might have something like 2 - 1. This will
confuse lookup_template_class, so we do constant folding
here. We have to unset processing_template_decl, to
fool build_expr_from_tree() into building an actual
tree. */
int saved_processing_template_decl = processing_template_decl;
processing_template_decl = 0;
elts[i] = fold (build_expr_from_tree (elts[i]));
processing_template_decl = saved_processing_template_decl;
}
if (elts[i] != TREE_VEC_ELT (t, i)) if (elts[i] != TREE_VEC_ELT (t, i))
need_new = 1; need_new = 1;
} }
...@@ -2305,8 +2337,16 @@ tree ...@@ -2305,8 +2337,16 @@ tree
do_poplevel () do_poplevel ()
{ {
tree t; tree t;
int saved_warn_unused;
if (processing_template_decl)
{
saved_warn_unused = warn_unused;
warn_unused = 0;
}
expand_end_bindings (getdecls (), kept_level_p (), 1); expand_end_bindings (getdecls (), kept_level_p (), 1);
if (processing_template_decl)
warn_unused = saved_warn_unused;
t = poplevel (kept_level_p (), 1, 0); t = poplevel (kept_level_p (), 1, 0);
pop_momentary (); pop_momentary ();
return t; return t;
...@@ -3566,7 +3606,7 @@ most_specialized_class (specs, mainargs) ...@@ -3566,7 +3606,7 @@ most_specialized_class (specs, mainargs)
for (t = list; t && t != champ; t = TREE_CHAIN (t)) for (t = list; t && t != champ; t = TREE_CHAIN (t))
{ {
fate = more_specialized (champ, t); fate = more_specialized_class (champ, t);
if (fate != 1) if (fate != 1)
return error_mark_node; return error_mark_node;
} }
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment