Commit aff08c18 by Jason Merrill Committed by Jason Merrill

cp-tree.h (struct lang_type): Add com_interface.

	* cp-tree.h (struct lang_type): Add com_interface.
	(CLASSTYPE_COM_INTERFACE): New macro.
	* class.c (set_rtti_entry): COM interface classes have no RTTI
	entries in their vtables; adjust.
	(add_virtual_function, finish_base_struct, skip_rtti_stuff,
	modify_one_vtable, fixup_vtable_deltas1, override_one_vtable,
	finish_struct_1): Likewise.
	* decl2.c (mark_vtable_entries): Likewise.
	* rtti.c (build_headof, get_tinfo_fn_dynamic): Likewise.
	* search.c (get_abstract_virtuals_1, get_abstract_virtuals,
	expand_upcast_fixups): Likewise.
	* tree.c (debug_binfo): Likewise.

From-SVN: r26394
parent 940ff223
1999-04-12 Jason Merrill <jason@yorick.cygnus.com> 1999-04-12 Jason Merrill <jason@yorick.cygnus.com>
* cp-tree.h (struct lang_type): Add com_interface.
(CLASSTYPE_COM_INTERFACE): New macro.
* class.c (set_rtti_entry): COM interface classes have no RTTI
entries in their vtables; adjust.
(add_virtual_function, finish_base_struct, skip_rtti_stuff,
modify_one_vtable, fixup_vtable_deltas1, override_one_vtable,
finish_struct_1): Likewise.
* decl2.c (mark_vtable_entries): Likewise.
* rtti.c (build_headof, get_tinfo_fn_dynamic): Likewise.
* search.c (get_abstract_virtuals_1, get_abstract_virtuals,
expand_upcast_fixups): Likewise.
* tree.c (debug_binfo): Likewise.
* cp-tree.h (COMPARE_NO_ATTRIBUTES): New macro. * cp-tree.h (COMPARE_NO_ATTRIBUTES): New macro.
* typeck.c (comptypes): If we get it, ignore attributes. * typeck.c (comptypes): If we get it, ignore attributes.
* class.c (instantiate_type): Use BASELINK_P. Change complain * class.c (instantiate_type): Use BASELINK_P. Change complain
......
...@@ -671,6 +671,9 @@ set_rtti_entry (virtuals, offset, type) ...@@ -671,6 +671,9 @@ set_rtti_entry (virtuals, offset, type)
{ {
tree vfn; tree vfn;
if (CLASSTYPE_COM_INTERFACE (type))
return;
if (flag_rtti) if (flag_rtti)
vfn = build1 (ADDR_EXPR, vfunc_ptr_type_node, get_tinfo_fn (type)); vfn = build1 (ADDR_EXPR, vfunc_ptr_type_node, get_tinfo_fn (type));
else else
...@@ -1035,10 +1038,14 @@ add_virtual_function (pv, phv, has_virtual, fndecl, t) ...@@ -1035,10 +1038,14 @@ add_virtual_function (pv, phv, has_virtual, fndecl, t)
CLASSTYPE_RTTI (t) = t; CLASSTYPE_RTTI (t) = t;
/* If we are using thunks, use two slots at the front, one /* If we are using thunks, use two slots at the front, one
for the offset pointer, one for the tdesc pointer. */ for the offset pointer, one for the tdesc pointer.
if (*has_virtual == 0 && flag_vtable_thunks) For ARM-style vtables, use the same slot for both. */
if (*has_virtual == 0 && ! CLASSTYPE_COM_INTERFACE (t))
{ {
*has_virtual = 1; if (flag_vtable_thunks)
*has_virtual = 2;
else
*has_virtual = 1;
} }
/* Build a new INT_CST for this DECL_VINDEX. */ /* Build a new INT_CST for this DECL_VINDEX. */
...@@ -1046,7 +1053,7 @@ add_virtual_function (pv, phv, has_virtual, fndecl, t) ...@@ -1046,7 +1053,7 @@ add_virtual_function (pv, phv, has_virtual, fndecl, t)
static tree index_table[256]; static tree index_table[256];
tree idx; tree idx;
/* We skip a slot for the offset/tdesc entry. */ /* We skip a slot for the offset/tdesc entry. */
int i = ++(*has_virtual); int i = (*has_virtual)++;
if (i >= 256 || index_table[i] == 0) if (i >= 256 || index_table[i] == 0)
{ {
...@@ -1634,6 +1641,21 @@ finish_base_struct (t, b) ...@@ -1634,6 +1641,21 @@ finish_base_struct (t, b)
TYPE_OVERLOADS_ARRAY_REF (t) |= TYPE_OVERLOADS_ARRAY_REF (basetype); TYPE_OVERLOADS_ARRAY_REF (t) |= TYPE_OVERLOADS_ARRAY_REF (basetype);
TYPE_OVERLOADS_ARROW (t) |= TYPE_OVERLOADS_ARROW (basetype); TYPE_OVERLOADS_ARROW (t) |= TYPE_OVERLOADS_ARROW (basetype);
if (CLASSTYPE_COM_INTERFACE (basetype))
{
CLASSTYPE_COM_INTERFACE (t) = 1;
if (i > 0)
cp_error
("COM interface type `%T' must be the leftmost base class",
basetype);
}
else if (CLASSTYPE_COM_INTERFACE (t))
{
cp_error ("COM interface type `%T' with non-COM base class `%T'",
t, basetype);
CLASSTYPE_COM_INTERFACE (t) = 0;
}
if (TYPE_VIRTUAL_P (basetype)) if (TYPE_VIRTUAL_P (basetype))
{ {
/* Ensure that this is set from at least a virtual base /* Ensure that this is set from at least a virtual base
...@@ -2285,11 +2307,14 @@ get_class_offset (context, t, binfo, fndecl) ...@@ -2285,11 +2307,14 @@ get_class_offset (context, t, binfo, fndecl)
/* Skip RTTI information at the front of the virtual list. */ /* Skip RTTI information at the front of the virtual list. */
unsigned HOST_WIDE_INT unsigned HOST_WIDE_INT
skip_rtti_stuff (virtuals) skip_rtti_stuff (virtuals, t)
tree *virtuals; tree *virtuals, t;
{ {
int n; int n;
if (CLASSTYPE_COM_INTERFACE (t))
return 0;
n = 0; n = 0;
if (*virtuals) if (*virtuals)
{ {
...@@ -2331,7 +2356,7 @@ modify_one_vtable (binfo, t, fndecl, pfn) ...@@ -2331,7 +2356,7 @@ modify_one_vtable (binfo, t, fndecl, pfn)
if (fndecl == NULL_TREE) if (fndecl == NULL_TREE)
return; return;
n = skip_rtti_stuff (&virtuals); n = skip_rtti_stuff (&virtuals, t);
while (virtuals) while (virtuals)
{ {
...@@ -2425,7 +2450,7 @@ fixup_vtable_deltas1 (binfo, t) ...@@ -2425,7 +2450,7 @@ fixup_vtable_deltas1 (binfo, t)
tree virtuals = BINFO_VIRTUALS (binfo); tree virtuals = BINFO_VIRTUALS (binfo);
unsigned HOST_WIDE_INT n; unsigned HOST_WIDE_INT n;
n = skip_rtti_stuff (&virtuals); n = skip_rtti_stuff (&virtuals, t);
while (virtuals) while (virtuals)
{ {
...@@ -2598,8 +2623,8 @@ override_one_vtable (binfo, old, t) ...@@ -2598,8 +2623,8 @@ override_one_vtable (binfo, old, t)
if (BINFO_NEW_VTABLE_MARKED (binfo)) if (BINFO_NEW_VTABLE_MARKED (binfo))
choose = NEITHER; choose = NEITHER;
skip_rtti_stuff (&virtuals); skip_rtti_stuff (&virtuals, t);
skip_rtti_stuff (&old_virtuals); skip_rtti_stuff (&old_virtuals, t);
while (virtuals) while (virtuals)
{ {
...@@ -3874,15 +3899,18 @@ finish_struct_1 (t, warn_anon) ...@@ -3874,15 +3899,18 @@ finish_struct_1 (t, warn_anon)
/* We must enter these virtuals into the table. */ /* We must enter these virtuals into the table. */
if (first_vfn_base_index < 0) if (first_vfn_base_index < 0)
{ {
/* The second slot is for the tdesc pointer when thunks are used. */ if (! CLASSTYPE_COM_INTERFACE (t))
if (flag_vtable_thunks) {
pending_virtuals = tree_cons (NULL_TREE, NULL_TREE, pending_virtuals); /* The second slot is for the tdesc pointer when thunks are used. */
if (flag_vtable_thunks)
pending_virtuals = tree_cons (NULL_TREE, NULL_TREE, pending_virtuals);
/* The first slot is for the rtti offset. */ /* The first slot is for the rtti offset. */
pending_virtuals = tree_cons (NULL_TREE, NULL_TREE, pending_virtuals); pending_virtuals = tree_cons (NULL_TREE, NULL_TREE, pending_virtuals);
set_rtti_entry (pending_virtuals, set_rtti_entry (pending_virtuals,
convert (ssizetype, integer_zero_node), t); convert (ssizetype, integer_zero_node), t);
}
build_vtable (NULL_TREE, t); build_vtable (NULL_TREE, t);
} }
else else
......
...@@ -736,11 +736,12 @@ struct lang_type ...@@ -736,11 +736,12 @@ struct lang_type
unsigned non_aggregate : 1; unsigned non_aggregate : 1;
unsigned is_partial_instantiation : 1; unsigned is_partial_instantiation : 1;
unsigned has_mutable : 1; unsigned has_mutable : 1;
unsigned com_interface : 1;
/* The MIPS compiler gets it wrong if this struct also /* The MIPS compiler gets it wrong if this struct also
does not fill out to a multiple of 4 bytes. Add a does not fill out to a multiple of 4 bytes. Add a
member `dummy' with new bits if you go over the edge. */ member `dummy' with new bits if you go over the edge. */
unsigned dummy : 11; unsigned dummy : 10;
} type_flags; } type_flags;
int vsize; int vsize;
...@@ -1010,6 +1011,10 @@ struct lang_type ...@@ -1010,6 +1011,10 @@ struct lang_type
#define CLASSTYPE_HAS_MUTABLE(NODE) (TYPE_LANG_SPECIFIC(NODE)->type_flags.has_mutable) #define CLASSTYPE_HAS_MUTABLE(NODE) (TYPE_LANG_SPECIFIC(NODE)->type_flags.has_mutable)
#define TYPE_HAS_MUTABLE_P(NODE) (cp_has_mutable_p (NODE)) #define TYPE_HAS_MUTABLE_P(NODE) (cp_has_mutable_p (NODE))
/* Nonzero means that this type is meant for communication via COM. */
#define CLASSTYPE_COM_INTERFACE(NODE) \
(TYPE_LANG_SPECIFIC(NODE)->type_flags.com_interface)
/* A list of class types of which this type is a friend. The /* A list of class types of which this type is a friend. The
TREE_VALUE is normally a TYPE, but will be a TEMPLATE_DECL in the TREE_VALUE is normally a TYPE, but will be a TEMPLATE_DECL in the
case of a template friend. */ case of a template friend. */
...@@ -2724,7 +2729,7 @@ extern void pop_lang_context PROTO((void)); ...@@ -2724,7 +2729,7 @@ extern void pop_lang_context PROTO((void));
extern tree instantiate_type PROTO((tree, tree, int)); extern tree instantiate_type PROTO((tree, tree, int));
extern void print_class_statistics PROTO((void)); extern void print_class_statistics PROTO((void));
extern void maybe_push_cache_obstack PROTO((void)); extern void maybe_push_cache_obstack PROTO((void));
extern unsigned HOST_WIDE_INT skip_rtti_stuff PROTO((tree *)); extern unsigned HOST_WIDE_INT skip_rtti_stuff PROTO((tree *, tree));
extern void build_self_reference PROTO((void)); extern void build_self_reference PROTO((void));
extern void warn_hidden PROTO((tree)); extern void warn_hidden PROTO((tree));
extern tree get_enclosing_class PROTO((tree)); extern tree get_enclosing_class PROTO((tree));
......
...@@ -2339,21 +2339,18 @@ mark_vtable_entries (decl) ...@@ -2339,21 +2339,18 @@ mark_vtable_entries (decl)
{ {
tree entries = CONSTRUCTOR_ELTS (DECL_INITIAL (decl)); tree entries = CONSTRUCTOR_ELTS (DECL_INITIAL (decl));
if (flag_rtti)
{
tree fnaddr = (flag_vtable_thunks ? TREE_VALUE (TREE_CHAIN (entries))
: FNADDR_FROM_VTABLE_ENTRY (TREE_VALUE (entries)));
tree fn = TREE_OPERAND (fnaddr, 0);
TREE_ADDRESSABLE (fn) = 1;
mark_used (fn);
}
skip_rtti_stuff (&entries);
for (; entries; entries = TREE_CHAIN (entries)) for (; entries; entries = TREE_CHAIN (entries))
{ {
tree fnaddr = (flag_vtable_thunks ? TREE_VALUE (entries) tree fnaddr;
: FNADDR_FROM_VTABLE_ENTRY (TREE_VALUE (entries))); tree fn;
tree fn = TREE_OPERAND (fnaddr, 0);
if (TREE_CODE (TREE_VALUE (entries)) == NOP_EXPR)
/* RTTI offset. */
continue;
fnaddr = (flag_vtable_thunks ? TREE_VALUE (entries)
: FNADDR_FROM_VTABLE_ENTRY (TREE_VALUE (entries)));
fn = TREE_OPERAND (fnaddr, 0);
TREE_ADDRESSABLE (fn) = 1; TREE_ADDRESSABLE (fn) = 1;
if (DECL_LANG_SPECIFIC (fn) && DECL_ABSTRACT_VIRTUAL_P (fn)) if (DECL_LANG_SPECIFIC (fn) && DECL_ABSTRACT_VIRTUAL_P (fn))
{ {
......
...@@ -108,6 +108,11 @@ build_headof (exp) ...@@ -108,6 +108,11 @@ build_headof (exp)
if (!TYPE_VIRTUAL_P (type)) if (!TYPE_VIRTUAL_P (type))
return exp; return exp;
if (CLASSTYPE_COM_INTERFACE (type))
{
cp_error ("RTTI not supported for COM interface type `%T'", type);
return error_mark_node;
}
/* If we don't have rtti stuff, get to a sub-object that does. */ /* If we don't have rtti stuff, get to a sub-object that does. */
if (!CLASSTYPE_VFIELDS (TREE_TYPE (TREE_TYPE (exp)))) if (!CLASSTYPE_VFIELDS (TREE_TYPE (TREE_TYPE (exp))))
...@@ -216,6 +221,11 @@ get_tinfo_fn_dynamic (exp) ...@@ -216,6 +221,11 @@ get_tinfo_fn_dynamic (exp)
if (! flag_rtti) if (! flag_rtti)
error ("taking dynamic typeid of object with -fno-rtti"); error ("taking dynamic typeid of object with -fno-rtti");
if (CLASSTYPE_COM_INTERFACE (type))
{
cp_error ("RTTI not supported for COM interface type `%T'", type);
return error_mark_node;
}
/* If we don't have rtti stuff, get to a sub-object that does. */ /* If we don't have rtti stuff, get to a sub-object that does. */
if (! CLASSTYPE_VFIELDS (type)) if (! CLASSTYPE_VFIELDS (type))
......
...@@ -2034,7 +2034,7 @@ get_abstract_virtuals_1 (binfo, do_self, abstract_virtuals) ...@@ -2034,7 +2034,7 @@ get_abstract_virtuals_1 (binfo, do_self, abstract_virtuals)
{ {
tree virtuals = BINFO_VIRTUALS (binfo); tree virtuals = BINFO_VIRTUALS (binfo);
skip_rtti_stuff (&virtuals); skip_rtti_stuff (&virtuals, BINFO_TYPE (binfo));
while (virtuals) while (virtuals)
{ {
...@@ -2067,7 +2067,7 @@ get_abstract_virtuals (type) ...@@ -2067,7 +2067,7 @@ get_abstract_virtuals (type)
{ {
tree virtuals = BINFO_VIRTUALS (vbases); tree virtuals = BINFO_VIRTUALS (vbases);
skip_rtti_stuff (&virtuals); skip_rtti_stuff (&virtuals, type);
while (virtuals) while (virtuals)
{ {
...@@ -2528,7 +2528,7 @@ expand_upcast_fixups (binfo, addr, orig_addr, vbase, vbase_addr, t, ...@@ -2528,7 +2528,7 @@ expand_upcast_fixups (binfo, addr, orig_addr, vbase, vbase_addr, t,
*vbase_offsets = delta; *vbase_offsets = delta;
} }
n = skip_rtti_stuff (&virtuals); n = skip_rtti_stuff (&virtuals, t);
while (virtuals) while (virtuals)
{ {
......
...@@ -1169,7 +1169,7 @@ debug_binfo (elem) ...@@ -1169,7 +1169,7 @@ debug_binfo (elem)
fprintf (stderr, "virtuals:\n"); fprintf (stderr, "virtuals:\n");
virtuals = BINFO_VIRTUALS (elem); virtuals = BINFO_VIRTUALS (elem);
n = skip_rtti_stuff (&virtuals); n = skip_rtti_stuff (&virtuals, BINFO_TYPE (elem));
while (virtuals) while (virtuals)
{ {
......
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