cp-tree.h (TYPE_BINFO): Update comment.

* cp-tree.h (TYPE_BINFO): Update comment.
	(BOUND_TEMPLATE_TEMPLATE_PARM_TYPE_CHECK): New macro.
	(TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO): Use template_info.
	(TYPENAME_TYPE_FULLNAME): Use TYPE_FIELDS.
	(copy_type): Prototype new function.
	* lex.c (copy_lang_decl): Gather tree node statistics.
	(copy_lang_type): New function.
	(copy_type): Likewise.
	(cp_make_lang_type): Create lang_type for
	BOUND_TEMPLATE_TEMPLATE_PARM.  Set TYPE_BINFO for TYPENAME_TYPE
	and BOUND_TEMPLATE_TEMPLATE_PARM.
	* pt.c (tsubst): Use copy_type instead of copy_node.
	* search.c (lookup_field_1): Ignore TYPENAME_TYPE.

From-SVN: r46244
This commit is contained in:
Kriang Lerdsuwanakij 2001-10-13 13:24:34 +00:00 committed by Kriang Lerdsuwanakij
parent f5d47abdf7
commit 11e74ea6c6
7 changed files with 112 additions and 18 deletions

View File

@ -1,3 +1,19 @@
2001-10-12 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
* cp-tree.h (TYPE_BINFO): Update comment.
(BOUND_TEMPLATE_TEMPLATE_PARM_TYPE_CHECK): New macro.
(TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO): Use template_info.
(TYPENAME_TYPE_FULLNAME): Use TYPE_FIELDS.
(copy_type): Prototype new function.
* lex.c (copy_lang_decl): Gather tree node statistics.
(copy_lang_type): New function.
(copy_type): Likewise.
(cp_make_lang_type): Create lang_type for
BOUND_TEMPLATE_TEMPLATE_PARM. Set TYPE_BINFO for TYPENAME_TYPE
and BOUND_TEMPLATE_TEMPLATE_PARM.
* pt.c (tsubst): Use copy_type instead of copy_node.
* search.c (lookup_field_1): Ignore TYPENAME_TYPE.
2001-10-12 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net> 2001-10-12 Kriang Lerdsuwanakij <lerdsuwa@users.sourceforge.net>
* pt.c (determine_specialization): Ignore functions without * pt.c (determine_specialization): Ignore functions without

View File

@ -114,9 +114,6 @@ Boston, MA 02111-1307, USA. */
TYPE_BINFO TYPE_BINFO
For an ENUMERAL_TYPE, this is ENUM_TEMPLATE_INFO. For an ENUMERAL_TYPE, this is ENUM_TEMPLATE_INFO.
For a TYPENAME_TYPE, this is TYPENAME_TYPE_FULLNAME.
For a TEMPLATE_TEMPLATE_PARM or BOUND_TEMPLATE_TEMPLATE_PARM,
this is TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO.
For a FUNCTION_TYPE or METHOD_TYPE, this is TYPE_RAISES_EXCEPTIONS For a FUNCTION_TYPE or METHOD_TYPE, this is TYPE_RAISES_EXCEPTIONS
BINFO_VIRTUALS BINFO_VIRTUALS
@ -193,6 +190,14 @@ Boston, MA 02111-1307, USA. */
__FUNCTION__); \ __FUNCTION__); \
__t; }) __t; })
#define BOUND_TEMPLATE_TEMPLATE_PARM_TYPE_CHECK(NODE) \
({ const tree __t = NODE; \
enum tree_code __c = TREE_CODE(__t); \
if (__c != BOUND_TEMPLATE_TEMPLATE_PARM) \
tree_check_failed (__t, BOUND_TEMPLATE_TEMPLATE_PARM, \
__FILE__, __LINE__, __FUNCTION__); \
__t; })
#else /* not ENABLE_TREE_CHECKING, or not gcc */ #else /* not ENABLE_TREE_CHECKING, or not gcc */
#define VAR_OR_FUNCTION_DECL_CHECK(NODE) NODE #define VAR_OR_FUNCTION_DECL_CHECK(NODE) NODE
@ -2147,8 +2152,10 @@ struct lang_decl
non-type template parameters. */ non-type template parameters. */
#define ENUM_TEMPLATE_INFO(NODE) (TYPE_BINFO (ENUMERAL_TYPE_CHECK (NODE))) #define ENUM_TEMPLATE_INFO(NODE) (TYPE_BINFO (ENUMERAL_TYPE_CHECK (NODE)))
/* Template information for a bound template template parameter. */ /* Template information for a template template parameter. */
#define TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO(NODE) (TYPE_BINFO (NODE)) #define TEMPLATE_TEMPLATE_PARM_TEMPLATE_INFO(NODE) \
(TYPE_LANG_SPECIFIC(BOUND_TEMPLATE_TEMPLATE_PARM_TYPE_CHECK (NODE)) \
->template_info)
/* Template information for an ENUMERAL_, RECORD_, or UNION_TYPE. */ /* Template information for an ENUMERAL_, RECORD_, or UNION_TYPE. */
#define TYPE_TEMPLATE_INFO(NODE) \ #define TYPE_TEMPLATE_INFO(NODE) \
@ -2311,7 +2318,7 @@ struct lang_decl
this is an IDENTIFIER_NODE, and the same as the DECL_NAME on the this is an IDENTIFIER_NODE, and the same as the DECL_NAME on the
corresponding TYPE_DECL. However, this may also be a corresponding TYPE_DECL. However, this may also be a
TEMPLATE_ID_EXPR if we had something like `typename X::Y<T>'. */ TEMPLATE_ID_EXPR if we had something like `typename X::Y<T>'. */
#define TYPENAME_TYPE_FULLNAME(NODE) TYPE_BINFO (NODE) #define TYPENAME_TYPE_FULLNAME(NODE) (TYPE_FIELDS (NODE))
/* Nonzero if NODE is an implicit typename. */ /* Nonzero if NODE is an implicit typename. */
#define IMPLICIT_TYPENAME_P(NODE) \ #define IMPLICIT_TYPENAME_P(NODE) \
@ -3859,6 +3866,7 @@ extern tree identifier_typedecl_value PARAMS ((tree));
extern tree build_lang_decl PARAMS ((enum tree_code, tree, tree)); extern tree build_lang_decl PARAMS ((enum tree_code, tree, tree));
extern void retrofit_lang_decl PARAMS ((tree)); extern void retrofit_lang_decl PARAMS ((tree));
extern tree copy_decl PARAMS ((tree)); extern tree copy_decl PARAMS ((tree));
extern tree copy_type PARAMS ((tree));
extern tree cp_make_lang_type PARAMS ((enum tree_code)); extern tree cp_make_lang_type PARAMS ((enum tree_code));
extern tree make_aggr_type PARAMS ((enum tree_code)); extern tree make_aggr_type PARAMS ((enum tree_code));
extern void compiler_error PARAMS ((const char *, ...)) extern void compiler_error PARAMS ((const char *, ...))

View File

@ -1552,6 +1552,11 @@ copy_lang_decl (node)
ld = (struct lang_decl *) ggc_alloc (size); ld = (struct lang_decl *) ggc_alloc (size);
memcpy (ld, DECL_LANG_SPECIFIC (node), size); memcpy (ld, DECL_LANG_SPECIFIC (node), size);
DECL_LANG_SPECIFIC (node) = ld; DECL_LANG_SPECIFIC (node) = ld;
#ifdef GATHER_STATISTICS
tree_node_counts[(int)lang_decl] += 1;
tree_node_sizes[(int)lang_decl] += size;
#endif
} }
/* Copy DECL, including any language-specific parts. */ /* Copy DECL, including any language-specific parts. */
@ -1567,14 +1572,51 @@ copy_decl (decl)
return copy; return copy;
} }
/* Replace the shared language-specific parts of NODE with a new copy. */
void
copy_lang_type (node)
tree node;
{
int size;
struct lang_type *lt;
if (! TYPE_LANG_SPECIFIC (node))
return;
size = sizeof (struct lang_type);
lt = (struct lang_type *) ggc_alloc (size);
memcpy (lt, TYPE_LANG_SPECIFIC (node), size);
TYPE_LANG_SPECIFIC (node) = lt;
#ifdef GATHER_STATISTICS
tree_node_counts[(int)lang_type] += 1;
tree_node_sizes[(int)lang_type] += size;
#endif
}
/* Copy TYPE, including any language-specific parts. */
tree
copy_type (type)
tree type;
{
tree copy;
copy = copy_node (type);
copy_lang_type (copy);
return copy;
}
tree tree
cp_make_lang_type (code) cp_make_lang_type (code)
enum tree_code code; enum tree_code code;
{ {
register tree t = make_node (code); register tree t = make_node (code);
/* Set up some flags that give proper default behavior. */ /* Create lang_type structure. */
if (IS_AGGR_TYPE_CODE (code)) if (IS_AGGR_TYPE_CODE (code)
|| code == BOUND_TEMPLATE_TEMPLATE_PARM)
{ {
struct lang_type *pi; struct lang_type *pi;
@ -1582,6 +1624,16 @@ cp_make_lang_type (code)
ggc_alloc_cleared (sizeof (struct lang_type))); ggc_alloc_cleared (sizeof (struct lang_type)));
TYPE_LANG_SPECIFIC (t) = pi; TYPE_LANG_SPECIFIC (t) = pi;
#ifdef GATHER_STATISTICS
tree_node_counts[(int)lang_type] += 1;
tree_node_sizes[(int)lang_type] += sizeof (struct lang_type);
#endif
}
/* Set up some flags that give proper default behavior. */
if (IS_AGGR_TYPE_CODE (code))
{
SET_CLASSTYPE_INTERFACE_UNKNOWN_X (t, interface_unknown); SET_CLASSTYPE_INTERFACE_UNKNOWN_X (t, interface_unknown);
CLASSTYPE_INTERFACE_ONLY (t) = interface_only; CLASSTYPE_INTERFACE_ONLY (t) = interface_only;
@ -1589,11 +1641,6 @@ cp_make_lang_type (code)
presence of parse errors, the normal was of assuring this presence of parse errors, the normal was of assuring this
might not ever get executed, so we lay it out *immediately*. */ might not ever get executed, so we lay it out *immediately*. */
build_pointer_type (t); build_pointer_type (t);
#ifdef GATHER_STATISTICS
tree_node_counts[(int)lang_type] += 1;
tree_node_sizes[(int)lang_type] += sizeof (struct lang_type);
#endif
} }
else else
/* We use TYPE_ALIAS_SET for the CLASSTYPE_MARKED bits. But, /* We use TYPE_ALIAS_SET for the CLASSTYPE_MARKED bits. But,
@ -1605,7 +1652,9 @@ cp_make_lang_type (code)
since they can be virtual base types, and we then need a since they can be virtual base types, and we then need a
canonical binfo for them. Ideally, this would be done lazily for canonical binfo for them. Ideally, this would be done lazily for
all types. */ all types. */
if (IS_AGGR_TYPE_CODE (code) || code == TEMPLATE_TYPE_PARM) if (IS_AGGR_TYPE_CODE (code) || code == TEMPLATE_TYPE_PARM
|| code == BOUND_TEMPLATE_TEMPLATE_PARM
|| code == TYPENAME_TYPE)
TYPE_BINFO (t) = make_binfo (size_zero_node, t, NULL_TREE, NULL_TREE); TYPE_BINFO (t) = make_binfo (size_zero_node, t, NULL_TREE, NULL_TREE);
return t; return t;

View File

@ -6429,7 +6429,7 @@ tsubst (t, args, complain, in_decl)
} }
else else
{ {
r = copy_node (t); r = copy_type (t);
TEMPLATE_TYPE_PARM_INDEX (r) TEMPLATE_TYPE_PARM_INDEX (r)
= reduce_template_parm_level (TEMPLATE_TYPE_PARM_INDEX (t), = reduce_template_parm_level (TEMPLATE_TYPE_PARM_INDEX (t),
r, levels); r, levels);

View File

@ -564,11 +564,14 @@ lookup_field_1 (type, name)
register tree field; register tree field;
if (TREE_CODE (type) == TEMPLATE_TYPE_PARM if (TREE_CODE (type) == TEMPLATE_TYPE_PARM
|| TREE_CODE (type) == BOUND_TEMPLATE_TEMPLATE_PARM) || TREE_CODE (type) == BOUND_TEMPLATE_TEMPLATE_PARM
/* The TYPE_FIELDS of a TEMPLATE_TYPE_PARM are not fields at all; || TREE_CODE (type) == TYPENAME_TYPE)
/* The TYPE_FIELDS of a TEMPLATE_TYPE_PARM and
BOUND_TEMPLATE_TEMPLATE_PARM are not fields at all;
instead TYPE_FIELDS is the TEMPLATE_PARM_INDEX. (Miraculously, instead TYPE_FIELDS is the TEMPLATE_PARM_INDEX. (Miraculously,
the code often worked even when we treated the index as a list the code often worked even when we treated the index as a list
of fields!) */ of fields!)
The TYPE_FIELDS of TYPENAME_TYPE is its TYPENAME_TYPE_FULLNAME. */
return NULL_TREE; return NULL_TREE;
if (TYPE_NAME (type) if (TYPE_NAME (type)

View File

@ -0,0 +1,9 @@
// Origin: Volker Reichelt <reichelt@igpm.rwth-aachen.de>
// { dg-do compile }
template <template <typename T> class A >
class B : virtual A<void>
{
typedef int INT;
INT i;
};

View File

@ -0,0 +1,9 @@
// Origin: Volker Reichelt <reichelt@igpm.rwth-aachen.de>
// { dg-do compile }
template <class T>
class B : virtual T::A
{
typedef int INT;
INT i;
};