Commit a55583e9 by Mark Mitchell Committed by Mark Mitchell

Don't create a separate copy of virtual bases for the CLASSTYPE_VBASECLASSES list.

	Don't create a separate copy of virtual bases for the
	CLASSTYPE_VBASECLASSES list.
	* cp-tree.h (CLASSTYPE_VBASECLASSES): Change documentation.
	(BINFO_FOR_VBASE): Remove.
	(CANONICAL_BINFO): Adjust.
	(binfo_for_vbase): New function.
	* class.c (build_vbase_pointer_fields): Use binfo_for_vbase
	instead of BINFO_FOR_VBASE.
	(build_vbase_pointer): Likewise.
	(build_secondary_vtable): Likewise.
	(dfs_mark_primary_bases): Likewise.
	(mark_primary_bases): Likewise.
	(layout_nonempty_base_or_field): Likewise.
	(dfs_set_offset_for_shared_vbases): Likewise.
	(dfs_set_offset_for_unshared_vbases): Likewise.
	(layout_virtual_bases): Likewise.  Adjust for changes to the
	CLASSTYPE_VBASECLASSES list.
	(dump_class_hierarchy_r): Use binfo_for_vbase
	instead of BINFO_FOR_VBASE.
	(dump_class_hierarchy): Likewise.
	(finish_vtbls): Likewise.
	(build_vtbl_initializer): Adjust for changes to the
	CLASSTYPE_VBASECLASSES list.
	(build_vbase_offset_vtbl_entries): Use binfo_for_vbase.
	* decl.c (finish_destructor_body): Adjust for changes to the
	CLASSTYPE_VBASECLASSES list.
	* init.c (sort_base_init): Use binfo_for_vbase.
	(construct_virtual_bases): Adjust for changes to the
	CLASSTYPE_VBASECLASSES list.
	(expand_member_init): Use binfo_for_vbase.
	(build_vbase_delete):  Adjust for changes to the
	CLASSTYPE_VBASECLASSES list.
	* method.c (do_build_copy_constructor): Likewise.
	* rtti.c (get_base_offset): Use binfo_for_vbase.
	(expand_class_desc): Remove #if 0'd code.
	* search.c (struct vbase_info): Remove vbase_types.
	(get_base_distance):  Use binfo_for_vbase.
	(lookup_field_queue_p): Use CANONICAL_BINFO.
	(get_shared_vbase_if_not_primary): Use binfo_for_vbase.
	(get_pure_virtuals): Adjust for changes to the
	CLASSTYPE_VBASECLASSES list.
	(dfs_find_vbases): Use binfo_for_vbase.
	(dfs_init_vbase_pointers): Likewise.
	(init_vbase_pointers): Don't initialize vi.vbase_types.
	(virtual_context): Use binfo_for_vbase.
	(fixup_all_virtual_upcast_offsets): Adjust for changes to the
	CLASSTYPE_VBASECLASSES list.
	(expand_indirect_vtbls_init): Simplify.
	(dfs_get_vbase_types): Don't replicate virtual bases.
	(find_vbase_instance): Use binfo_for_vbase.
	(binfo_for_vbase): New function.
	* typeck.c (get_delta_difference): Use binfo_for_vbase.

From-SVN: r34040
parent efc9bd41
2000-05-19 Mark Mitchell <mark@codesourcery.com>
Don't create a separate copy of virtual bases for the
CLASSTYPE_VBASECLASSES list.
* cp-tree.h (CLASSTYPE_VBASECLASSES): Change documentation.
(BINFO_FOR_VBASE): Remove.
(CANONICAL_BINFO): Adjust.
(binfo_for_vbase): New function.
* class.c (build_vbase_pointer_fields): Use binfo_for_vbase
instead of BINFO_FOR_VBASE.
(build_vbase_pointer): Likewise.
(build_secondary_vtable): Likewise.
(dfs_mark_primary_bases): Likewise.
(mark_primary_bases): Likewise.
(layout_nonempty_base_or_field): Likewise.
(dfs_set_offset_for_shared_vbases): Likewise.
(dfs_set_offset_for_unshared_vbases): Likewise.
(layout_virtual_bases): Likewise. Adjust for changes to the
CLASSTYPE_VBASECLASSES list.
(dump_class_hierarchy_r): Use binfo_for_vbase
instead of BINFO_FOR_VBASE.
(dump_class_hierarchy): Likewise.
(finish_vtbls): Likewise.
(build_vtbl_initializer): Adjust for changes to the
CLASSTYPE_VBASECLASSES list.
(build_vbase_offset_vtbl_entries): Use binfo_for_vbase.
* decl.c (finish_destructor_body): Adjust for changes to the
CLASSTYPE_VBASECLASSES list.
* init.c (sort_base_init): Use binfo_for_vbase.
(construct_virtual_bases): Adjust for changes to the
CLASSTYPE_VBASECLASSES list.
(expand_member_init): Use binfo_for_vbase.
(build_vbase_delete): Adjust for changes to the
CLASSTYPE_VBASECLASSES list.
* method.c (do_build_copy_constructor): Likewise.
* rtti.c (get_base_offset): Use binfo_for_vbase.
(expand_class_desc): Remove #if 0'd code.
* search.c (struct vbase_info): Remove vbase_types.
(get_base_distance): Use binfo_for_vbase.
(lookup_field_queue_p): Use CANONICAL_BINFO.
(get_shared_vbase_if_not_primary): Use binfo_for_vbase.
(get_pure_virtuals): Adjust for changes to the
CLASSTYPE_VBASECLASSES list.
(dfs_find_vbases): Use binfo_for_vbase.
(dfs_init_vbase_pointers): Likewise.
(init_vbase_pointers): Don't initialize vi.vbase_types.
(virtual_context): Use binfo_for_vbase.
(fixup_all_virtual_upcast_offsets): Adjust for changes to the
CLASSTYPE_VBASECLASSES list.
(expand_indirect_vtbls_init): Simplify.
(dfs_get_vbase_types): Don't replicate virtual bases.
(find_vbase_instance): Use binfo_for_vbase.
(binfo_for_vbase): New function.
* typeck.c (get_delta_difference): Use binfo_for_vbase.
2000-05-17 Mark Mitchell <mark@codesourcery.com>
* decl2.c (finish_anon_union): Generalize error messages to handle
......
......@@ -246,7 +246,7 @@ build_vbase_pointer_fields (rli, empty_p)
{
tree other_base_binfo = TREE_VEC_ELT (binfos, j);
if (! TREE_VIA_VIRTUAL (other_base_binfo)
&& BINFO_FOR_VBASE (basetype, BINFO_TYPE (other_base_binfo)))
&& binfo_for_vbase (basetype, BINFO_TYPE (other_base_binfo)))
goto got_it;
}
FORMAT_VBASE_NAME (name, basetype);
......@@ -285,7 +285,7 @@ build_vbase_pointer (exp, type)
/* Find the shared copy of TYPE; that's where the vtable offset
is recorded. */
vbase = BINFO_FOR_VBASE (type, TREE_TYPE (exp));
vbase = binfo_for_vbase (type, TREE_TYPE (exp));
/* Find the virtual function table pointer. */
vbase_ptr = build_vfield_ref (exp, TREE_TYPE (exp));
/* Compute the location where the offset will lie. */
......@@ -841,7 +841,7 @@ build_secondary_vtable (binfo, for_type)
#endif
if (TREE_VIA_VIRTUAL (binfo))
my_friendly_assert (binfo == BINFO_FOR_VBASE (BINFO_TYPE (binfo),
my_friendly_assert (binfo == binfo_for_vbase (BINFO_TYPE (binfo),
current_class_type),
170);
......@@ -859,7 +859,7 @@ build_secondary_vtable (binfo, for_type)
if (TREE_VIA_VIRTUAL (binfo))
{
tree binfo1 = BINFO_FOR_VBASE (BINFO_TYPE (binfo), for_type);
tree binfo1 = binfo_for_vbase (BINFO_TYPE (binfo), for_type);
/* XXX - This should never happen, if it does, the caller should
ensure that the binfo is from for_type's binfos, not from any
......@@ -1694,7 +1694,7 @@ dfs_mark_primary_bases (binfo, data)
tree shared_binfo;
shared_binfo
= BINFO_FOR_VBASE (BINFO_TYPE (base_binfo), (tree) data);
= binfo_for_vbase (BINFO_TYPE (base_binfo), (tree) data);
/* If this virtual base is not already primary somewhere else in
the hiearchy, then we'll be using this copy. */
......@@ -1741,7 +1741,7 @@ mark_primary_bases (type)
if (!TREE_VIA_VIRTUAL (vbases))
continue;
vbase = BINFO_FOR_VBASE (BINFO_TYPE (vbases), type);
vbase = binfo_for_vbase (BINFO_TYPE (vbases), type);
if (BINFO_VBASE_PRIMARY_P (vbase))
/* This virtual base was already included in the hierarchy, so
there's nothing to do here. */
......@@ -3667,7 +3667,7 @@ layout_nonempty_base_or_field (rli, decl, binfo, v)
a data member. */
if (binfo && flag_new_abi && layout_conflict_p (binfo, v))
{
/* Undo the propogate_binfo_offsets call. */
/* Undo the propagate_binfo_offsets call. */
offset = size_diffop (size_zero_node, offset);
propagate_binfo_offsets (binfo, convert (ssizetype, offset));
......@@ -4376,7 +4376,7 @@ dfs_set_offset_for_shared_vbases (binfo, data)
/* Update the shared copy. */
tree shared_binfo;
shared_binfo = BINFO_FOR_VBASE (BINFO_TYPE (binfo), (tree) data);
shared_binfo = binfo_for_vbase (BINFO_TYPE (binfo), (tree) data);
BINFO_OFFSET (shared_binfo) = BINFO_OFFSET (binfo);
}
......@@ -4399,7 +4399,7 @@ dfs_set_offset_for_unshared_vbases (binfo, data)
tree vbase;
tree offset;
vbase = BINFO_FOR_VBASE (BINFO_TYPE (binfo), t);
vbase = binfo_for_vbase (BINFO_TYPE (binfo), t);
offset = size_diffop (BINFO_OFFSET (vbase), BINFO_OFFSET (binfo));
propagate_binfo_offsets (binfo, offset);
}
......@@ -4448,13 +4448,14 @@ layout_virtual_bases (t, base_offsets)
{
tree vbase;
if (!TREE_VIA_VIRTUAL (vbases))
continue;
if (flag_new_abi)
vbase = BINFO_FOR_VBASE (BINFO_TYPE (vbases), t);
{
if (!TREE_VIA_VIRTUAL (vbases))
continue;
vbase = binfo_for_vbase (BINFO_TYPE (vbases), t);
}
else
vbase = vbases;
vbase = TREE_VALUE (vbases);
if (!BINFO_VBASE_PRIMARY_P (vbase))
{
......@@ -4486,9 +4487,15 @@ layout_virtual_bases (t, base_offsets)
*base_offsets);
else
{
tree offset;
offset = ssize_int (CEIL (dsize, BITS_PER_UNIT));
offset = size_diffop (offset,
convert (ssizetype,
BINFO_OFFSET (vbase)));
/* And compute the offset of the virtual base. */
propagate_binfo_offsets (vbase,
ssize_int (CEIL (dsize, BITS_PER_UNIT)));
propagate_binfo_offsets (vbase, offset);
/* Every virtual baseclass takes a least a UNIT, so that
we can take it's address and get something different
for each base. */
......@@ -4516,10 +4523,6 @@ layout_virtual_bases (t, base_offsets)
in get_base_distance depend on the BINFO_OFFSETs being set
correctly. */
dfs_walk (TYPE_BINFO (t), dfs_set_offset_for_unshared_vbases, NULL, t);
for (vbases = CLASSTYPE_VBASECLASSES (t);
vbases;
vbases = TREE_CHAIN (vbases))
dfs_walk (vbases, dfs_set_offset_for_unshared_vbases, NULL, t);
/* If we had empty base classes that protruded beyond the end of the
class, we didn't update DSIZE above; we were hoping to overlay
......@@ -4542,7 +4545,7 @@ layout_virtual_bases (t, base_offsets)
vbases;
vbases = TREE_CHAIN (vbases))
{
tree basetype = BINFO_TYPE (vbases);
tree basetype = BINFO_TYPE (TREE_VALUE (vbases));
if (get_base_distance (basetype, t, 0, (tree*)0) == -2)
cp_warning ("virtual base `%T' inaccessible in `%T' due to ambiguity",
basetype, t);
......@@ -6334,7 +6337,7 @@ dump_class_hierarchy_r (t, binfo, indent)
fprintf (stderr, " virtual");
if (BINFO_PRIMARY_MARKED_P (binfo)
|| (TREE_VIA_VIRTUAL (binfo)
&& BINFO_VBASE_PRIMARY_P (BINFO_FOR_VBASE (BINFO_TYPE (binfo),
&& BINFO_VBASE_PRIMARY_P (binfo_for_vbase (BINFO_TYPE (binfo),
t))))
fprintf (stderr, " primary");
fprintf (stderr, "\n");
......@@ -6349,12 +6352,7 @@ void
dump_class_hierarchy (t)
tree t;
{
tree vbase;
dump_class_hierarchy_r (t, TYPE_BINFO (t), 0);
fprintf (stderr, "virtual bases\n");
for (vbase = CLASSTYPE_VBASECLASSES (t); vbase; vbase = TREE_CHAIN (vbase))
dump_class_hierarchy_r (t, vbase, 0);
}
/* Virtual function table initialization. */
......@@ -6383,7 +6381,7 @@ finish_vtbls (t)
{
if (!TREE_VIA_VIRTUAL (vbase))
continue;
accumulate_vtbl_inits (BINFO_FOR_VBASE (BINFO_TYPE (vbase), t),
accumulate_vtbl_inits (binfo_for_vbase (BINFO_TYPE (vbase), t),
list);
}
......@@ -6554,7 +6552,7 @@ build_vtbl_initializer (binfo, original_binfo, t, rtti_binfo,
for (vbase = CLASSTYPE_VBASECLASSES (t);
vbase;
vbase = TREE_CHAIN (vbase))
CLEAR_BINFO_VTABLE_PATH_MARKED (vbase);
CLEAR_BINFO_VTABLE_PATH_MARKED (TREE_VALUE (vbase));
/* Add entries to the vtable for RTTI. */
inits = chainon (inits, build_rtti_vtbl_entries (binfo, rtti_binfo));
......@@ -6673,7 +6671,7 @@ build_vbase_offset_vtbl_entries (binfo, vod)
/* Find the instance of this virtual base in the complete
object. */
b = BINFO_FOR_VBASE (BINFO_TYPE (vbase), t);
b = binfo_for_vbase (BINFO_TYPE (vbase), t);
/* If we've already got an offset for this virtual base, we
don't need another one. */
......@@ -6694,7 +6692,7 @@ build_vbase_offset_vtbl_entries (binfo, vod)
tree orig_vbase;
/* Find the instance of this virtual base in the type of BINFO. */
orig_vbase = BINFO_FOR_VBASE (BINFO_TYPE (vbase),
orig_vbase = binfo_for_vbase (BINFO_TYPE (vbase),
BINFO_TYPE (binfo));
/* The vbase offset had better be the same. */
......
......@@ -1598,34 +1598,15 @@ struct lang_type
/* A chain of BINFOs for the direct and indirect virtual base classes
that this type uses in a post-order depth-first left-to-right
order. (In other words, these bases appear in the order that they
should be initialized.)
These BINFOs are distinct from those in the TYPE_BINFO hierarchy.
So, given:
struct A {};
struct B : public A {};
struct C : virtual public B {};
struct D : virtual public B {};
struct E : public C, public D {};
there will be two copies of `A' and `B' in the TYPE_BINFO hierarchy
for `E'. On the CLASSTYPE_VBASECLASSES list, there will be just
one copy of `B' (distinct from the other two) with its own copy of `A'
(also distinct from the copies in the TYPE_BINFO hierarchy.) */
should be initialized.) */
#define CLASSTYPE_VBASECLASSES(NODE) (TYPE_LANG_SPECIFIC(NODE)->vbases)
/* The BINFO (if any) for the virtual baseclass T of the class C from
the CLASSTYPE_VBASECLASSES list. */
#define BINFO_FOR_VBASE(T, C) \
(binfo_member (T, CLASSTYPE_VBASECLASSES (C)))
/* For a non-virtual BINFO, the BINFO itself; for a virtual BINFO, the
BINFO_FOR_VBASE. C is the most derived class for the hierarchy
binfo_for_vbase. C is the most derived class for the hierarchy
containing BINFO. */
#define CANONICAL_BINFO(BINFO, C) \
(TREE_VIA_VIRTUAL (BINFO) \
? BINFO_FOR_VBASE (BINFO_TYPE (BINFO), C) \
? binfo_for_vbase (BINFO_TYPE (BINFO), C) \
: BINFO)
/* Number of direct baseclasses of NODE. */
......@@ -1718,9 +1699,7 @@ struct lang_type
for B (in D) will have a BINFO_INHERITANCE_CHAIN pointing to
D. In tree.h, this pointer is described as pointing in other
direction. There is a different BINFO for each path to a virtual
base; BINFOs for virtual bases are not shared. In addition, shared
versions of each of the virtual class BINFOs are stored in
CLASSTYPE_VBASECLASSES.
base; BINFOs for virtual bases are not shared.
We use TREE_VIA_PROTECTED and TREE_VIA_PUBLIC, but private
inheritance is indicated by the absence of the other two flags, not
......@@ -1760,29 +1739,13 @@ struct lang_type
/* Nonzero if this BINFO is a primary base class.
In the TYPE_BINFO hierarchy, this flag is never set for a base
class of a non-primary virtual base because the copies of a
non-primary virtual base that appear in the TYPE_BINFO hierarchy do
not really exist. Instead, it is the BINFOs in the
CLASSTYPE_VBASECLASSES list that are used. In other words, this
flag is only valid for paths (given by BINFO_INHERITANCE_CHAIN)
that really exist in the final object.
For example, consider:
struct A {};
struct B : public A { };
struct C : virtual public B { void f(); int i; };
`A' is the primary base class for `B'. But, `B' is not a primary
base class for `C'. So, in the copy of `A' that appears in the
TYPE_BINFO hierarcy for `C' does not have BINFO_PRIMARY_MARKED_P
set; the copy in the CLASSTYPE_VBASECLASSES list does have this
set. */
class of a non-primary virtual base. This flag is only valid for
paths (given by BINFO_INHERITANCE_CHAIN) that really exist in the
final object. */
#define BINFO_PRIMARY_MARKED_P(NODE) TREE_LANG_FLAG_5 (NODE)
/* Nonzero if the virtual baseclass with the type given by this BINFO
is primary *somewhere* in the hierarchy. This flag is only set on
entries in the CLASSTYPE_VBASECLASSES list. */
is primary *somewhere* in the hierarchy. */
#define BINFO_VBASE_PRIMARY_P(NODE) TREE_LANG_FLAG_6 (NODE)
/* Used by various search routines. */
......@@ -4365,6 +4328,7 @@ extern tree marked_vtable_pathp PARAMS ((tree, void *));
extern tree unmarked_vtable_pathp PARAMS ((tree, void *));
extern tree convert_pointer_to_vbase PARAMS ((tree, tree));
extern tree find_vbase_instance PARAMS ((tree, tree));
extern tree binfo_for_vbase PARAMS ((tree, tree));
/* in semantics.c */
extern void finish_expr_stmt PARAMS ((tree));
......
......@@ -13863,26 +13863,34 @@ finish_destructor_body ()
/* Run destructors for all virtual baseclasses. */
if (TYPE_USES_VIRTUAL_BASECLASSES (current_class_type))
{
tree vbases = nreverse (copy_list (CLASSTYPE_VBASECLASSES (current_class_type)));
tree if_stmt = begin_if_stmt ();
tree vbases;
tree if_stmt;
if_stmt = begin_if_stmt ();
finish_if_stmt_cond (build (BIT_AND_EXPR, integer_type_node,
current_in_charge_parm,
integer_two_node),
if_stmt);
while (vbases)
vbases = CLASSTYPE_VBASECLASSES (current_class_type);
/* The CLASSTYPE_VBASECLASSES list is in initialization
order, so we have to march through it in reverse order. */
for (vbases = nreverse (copy_list (vbases));
vbases;
vbases = TREE_CHAIN (vbases))
{
if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (BINFO_TYPE (vbases)))
tree vbase = TREE_VALUE (vbases);
if (TYPE_HAS_NONTRIVIAL_DESTRUCTOR (BINFO_TYPE (vbase)))
{
tree vb = get_vbase
(BINFO_TYPE (vbases),
(BINFO_TYPE (vbase),
TYPE_BINFO (current_class_type));
finish_expr_stmt
(build_scoped_method_call
(current_class_ref, vb, base_dtor_identifier,
NULL_TREE));
}
vbases = TREE_CHAIN (vbases);
}
finish_then_clause (if_stmt);
......
......@@ -537,7 +537,7 @@ sort_base_init (t, rbase_ptr, vbase_ptr)
this constructor is the top-level constructor called. */
if (TREE_VIA_VIRTUAL (binfo))
{
tree v = BINFO_FOR_VBASE (BINFO_TYPE (binfo), t);
tree v = binfo_for_vbase (BINFO_TYPE (binfo), t);
vbases = tree_cons (v, TREE_VALUE (x), vbases);
continue;
}
......@@ -855,6 +855,7 @@ construct_virtual_bases (type, this_ref, this_ptr, init_list, flag)
tree inner_if_stmt;
tree compound_stmt;
tree exp;
tree vbase;
/* If there are virtual base classes with destructors, we need to
emit cleanups to destroy them if an exception is thrown during
......@@ -878,21 +879,22 @@ construct_virtual_bases (type, this_ref, this_ptr, init_list, flag)
constructing virtual bases, then we must be the most derived
class. Therefore, we don't have to look up the virtual base;
we already know where it is. */
vbase = TREE_VALUE (vbases);
exp = build (PLUS_EXPR,
TREE_TYPE (this_ptr),
this_ptr,
fold (build1 (NOP_EXPR, TREE_TYPE (this_ptr),
BINFO_OFFSET (vbases))));
BINFO_OFFSET (vbase))));
exp = build1 (NOP_EXPR,
build_pointer_type (BINFO_TYPE (vbases)),
build_pointer_type (BINFO_TYPE (vbase)),
exp);
expand_aggr_vbase_init_1 (vbases, this_ref, exp, init_list);
expand_aggr_vbase_init_1 (vbase, this_ref, exp, init_list);
finish_compound_stmt (/*has_no_scope=*/1, compound_stmt);
finish_then_clause (inner_if_stmt);
finish_if_stmt ();
expand_cleanup_for_base (vbases, flag);
expand_cleanup_for_base (vbase, flag);
}
}
......@@ -1022,7 +1024,7 @@ expand_member_init (exp, name, init)
&& ! current_template_parms
&& ! vec_binfo_member (basetype,
TYPE_BINFO_BASETYPES (type))
&& ! BINFO_FOR_VBASE (basetype, type))
&& ! binfo_for_vbase (basetype, type))
{
if (IDENTIFIER_CLASS_VALUE (name))
goto try_member;
......@@ -3290,8 +3292,9 @@ build_vbase_delete (type, decl)
while (vbases)
{
tree this_addr = convert_force (build_pointer_type (BINFO_TYPE (vbases)),
addr, 0);
tree this_addr
= convert_force (build_pointer_type (BINFO_TYPE (TREE_VALUE (vbases))),
addr, 0);
result = tree_cons (NULL_TREE,
build_delete (TREE_TYPE (this_addr), this_addr,
integer_zero_node,
......
......@@ -2262,7 +2262,8 @@ do_build_copy_constructor (fndecl)
for (t = CLASSTYPE_VBASECLASSES (current_class_type); t;
t = TREE_CHAIN (t))
current_base_init_list
= tree_cons (BINFO_TYPE (t), parm, current_base_init_list);
= tree_cons (BINFO_TYPE (TREE_VALUE (t)), parm,
current_base_init_list);
for (i = 0; i < n_bases; ++i)
{
t = TREE_VEC_ELT (binfos, i);
......
......@@ -548,7 +548,7 @@ get_base_offset (binfo, parent)
/* Under the new ABI, we store the vtable offset at which
the virtual base offset can be found. */
return convert (sizetype,
BINFO_VPTR_FIELD (BINFO_FOR_VBASE (BINFO_TYPE (binfo),
BINFO_VPTR_FIELD (binfo_for_vbase (BINFO_TYPE (binfo),
parent)));
}
......@@ -930,11 +930,6 @@ expand_class_desc (tdecl, type)
int i = CLASSTYPE_N_BASECLASSES (type);
int base_cnt = 0;
tree binfos = TYPE_BINFO_BASETYPES (type);
#if 0
/* See code below that used these. */
tree vb = CLASSTYPE_VBASECLASSES (type);
int n_base = i;
#endif
tree base, elems, access, offset, isvir;
tree elt, elts = NULL_TREE;
......@@ -1000,39 +995,6 @@ expand_class_desc (tdecl, type)
elts = tree_cons (NULL_TREE, elt, elts);
base_cnt++;
}
#if 0
i = n_base;
while (vb)
{
tree b;
access = access_public_node;
while (--i >= 0)
{
b = TREE_VEC_ELT (binfos, i);
if (BINFO_TYPE (vb) == BINFO_TYPE (b) && TREE_VIA_VIRTUAL (b))
{
if (TREE_VIA_PUBLIC (b))
access = access_public_node;
else if (TREE_VIA_PROTECTED (b))
access = access_protected_node;
else
access = access_private_node;
break;
}
}
base = build_t_desc (BINFO_TYPE (vb), 1);
offset = BINFO_OFFSET (vb);
isvir = build_int_2 (1, 0);
base_list = tree_cons (NULL_TREE, base, base_list);
isvir_list = tree_cons (NULL_TREE, isvir, isvir_list);
acc_list = tree_cons (NULL_TREE, access, acc_list);
off_list = tree_cons (NULL_TREE, offset, off_list);
base_cnt++;
vb = TREE_CHAIN (vb);
}
#endif
name_string = tinfo_name (type);
......
......@@ -82,7 +82,6 @@ struct vbase_info
tree type;
tree decl_ptr;
tree inits;
tree vbase_types;
};
static tree next_baselink PARAMS ((tree));
......@@ -491,9 +490,8 @@ get_base_distance (parent, binfo, protect, path_ptr)
tree, deal with it. This happens when we are called from
expand_upcast_fixups. */
if (rval == -1 && TREE_CODE (parent) == TREE_VEC
&& parent == BINFO_FOR_VBASE (BINFO_TYPE (parent), type))
&& parent == binfo_for_vbase (BINFO_TYPE (parent), type))
{
my_friendly_assert (BINFO_INHERITANCE_CHAIN (parent) == binfo, 980827);
new_binfo = parent;
rval = 1;
}
......@@ -1351,10 +1349,7 @@ lookup_field_queue_p (binfo, data)
&& hides (lfi->rval_binfo, binfo))
return NULL_TREE;
if (TREE_VIA_VIRTUAL (binfo))
return BINFO_FOR_VBASE (BINFO_TYPE (binfo), lfi->type);
else
return binfo;
return CANONICAL_BINFO (binfo, lfi->type);
}
/* Within the scope of a template class, you can refer to the to the
......@@ -2230,7 +2225,7 @@ get_shared_vbase_if_not_primary (binfo, data)
/* This is a non-primary virtual base. If there is no primary
version, get the shared version. */
binfo = BINFO_FOR_VBASE (BINFO_TYPE (binfo), type);
binfo = binfo_for_vbase (BINFO_TYPE (binfo), type);
if (BINFO_VBASE_PRIMARY_P (binfo))
return NULL_TREE;
}
......@@ -2344,7 +2339,7 @@ get_pure_virtuals (type)
{
tree virtuals;
for (virtuals = BINFO_VIRTUALS (vbases);
for (virtuals = BINFO_VIRTUALS (TREE_VALUE (vbases));
virtuals;
virtuals = TREE_CHAIN (virtuals))
{
......@@ -2492,7 +2487,7 @@ dfs_find_vbases (binfo, data)
&& CLASSTYPE_SEARCH_SLOT (BINFO_TYPE (base_binfo)) == 0)
{
tree vbase = BINFO_TYPE (base_binfo);
tree binfo = binfo_member (vbase, vi->vbase_types);
tree binfo = binfo_for_vbase (vbase, vi->type);
tree ptr_type = build_pointer_type (vbase);
CLASSTYPE_SEARCH_SLOT (vbase)
......@@ -2546,10 +2541,11 @@ dfs_init_vbase_pointers (binfo, data)
tree ref = build (COMPONENT_REF, TREE_TYPE (fields),
build_indirect_ref (this_vbase_ptr, NULL_PTR), fields);
tree init = CLASSTYPE_SEARCH_SLOT (TREE_TYPE (TREE_TYPE (fields)));
vi->inits = tree_cons (binfo_member (TREE_TYPE (TREE_TYPE (fields)),
vi->vbase_types),
build_modify_expr (ref, NOP_EXPR, init),
vi->inits);
vi->inits
= tree_cons (binfo_for_vbase (TREE_TYPE (TREE_TYPE (fields)),
vi->type),
build_modify_expr (ref, NOP_EXPR, init),
vi->inits);
fields = TREE_CHAIN (fields);
}
......@@ -2590,7 +2586,6 @@ init_vbase_pointers (type, decl_ptr)
initialization. */
vi.type = type;
vi.decl_ptr = decl_ptr;
vi.vbase_types = CLASSTYPE_VBASECLASSES (type);
vi.inits = NULL_TREE;
dfs_walk (binfo, dfs_find_vbases, unmarked_vtable_pathp, &vi);
......@@ -2635,7 +2630,7 @@ virtual_context (fndecl, t, vbase)
/* Not sure if checking path == vbase is necessary here, but just in
case it is. */
if (TREE_VIA_VIRTUAL (path) || path == vbase)
return BINFO_FOR_VBASE (BINFO_TYPE (path), t);
return binfo_for_vbase (BINFO_TYPE (path), t);
path = BINFO_INHERITANCE_CHAIN (path);
}
}
......@@ -2646,7 +2641,7 @@ virtual_context (fndecl, t, vbase)
while (path)
{
if (TREE_VIA_VIRTUAL (path))
return BINFO_FOR_VBASE (BINFO_TYPE (path), t);
return binfo_for_vbase (BINFO_TYPE (path), t);
path = BINFO_INHERITANCE_CHAIN (path);
}
return 0;
......@@ -2873,11 +2868,11 @@ fixup_all_virtual_upcast_offsets (type, decl_ptr)
tree vbase_offsets;
tree addr;
vbase = find_vbase_instance (BINFO_TYPE (vbases), type);
vbase = find_vbase_instance (TREE_PURPOSE (vbases), type);
vbase_offsets = NULL_TREE;
addr = convert_pointer_to_vbase (BINFO_TYPE (vbases), decl_ptr);
addr = convert_pointer_to_vbase (TREE_PURPOSE (vbases), decl_ptr);
fixup_virtual_upcast_offsets (vbase,
TYPE_BINFO (BINFO_TYPE (vbases)),
TYPE_BINFO (TREE_PURPOSE (vbases)),
1, 0, addr, decl_ptr,
type, vbase, &vbase_offsets);
}
......@@ -2916,11 +2911,9 @@ expand_indirect_vtbls_init (binfo, decl_ptr)
if (TYPE_USES_VIRTUAL_BASECLASSES (type))
{
tree vbases = CLASSTYPE_VBASECLASSES (type);
struct vbase_info vi;
vi.type = type;
vi.decl_ptr = decl_ptr;
vi.vbase_types = vbases;
dfs_walk (binfo, dfs_find_vbases, NULL, &vi);
fixup_all_virtual_upcast_offsets (type, vi.decl_ptr);
......@@ -2940,17 +2933,10 @@ dfs_get_vbase_types (binfo, data)
tree type = (tree) data;
if (TREE_VIA_VIRTUAL (binfo))
{
tree new_vbase = make_binfo (size_zero_node,
BINFO_TYPE (binfo),
BINFO_VTABLE (binfo),
BINFO_VIRTUALS (binfo));
unshare_base_binfos (new_vbase);
TREE_VIA_VIRTUAL (new_vbase) = 1;
BINFO_INHERITANCE_CHAIN (new_vbase) = TYPE_BINFO (type);
TREE_CHAIN (new_vbase) = CLASSTYPE_VBASECLASSES (type);
CLASSTYPE_VBASECLASSES (type) = new_vbase;
}
CLASSTYPE_VBASECLASSES (type)
= tree_cons (BINFO_TYPE (binfo),
binfo,
CLASSTYPE_VBASECLASSES (type));
SET_BINFO_MARKED (binfo);
return NULL_TREE;
}
......@@ -3022,7 +3008,7 @@ find_vbase_instance (base, type)
{
tree instance;
instance = BINFO_FOR_VBASE (base, type);
instance = binfo_for_vbase (base, type);
if (!BINFO_VBASE_PRIMARY_P (instance))
return instance;
......@@ -3527,3 +3513,17 @@ binfo_from_vbase (binfo)
}
return 0;
}
/* Returns the BINFO (if any) for the virtual baseclass T of the class
C from the CLASSTYPE_VBASECLASSES list. */
tree
binfo_for_vbase (basetype, classtype)
tree basetype;
tree classtype;
{
tree binfo;
binfo = purpose_member (basetype, CLASSTYPE_VBASECLASSES (classtype));
return binfo ? TREE_VALUE (binfo) : NULL_TREE;
}
......@@ -5986,11 +5986,10 @@ get_delta_difference (from, to, force)
if (to == from)
return delta;
/* Should get_base_distance here, so we can check if any thing along the
path is virtual, and we need to make sure we stay
inside the real binfos when going through virtual bases.
Maybe we should replace virtual bases with
binfo_member (...CLASSTYPE_VBASECLASSES...)... (mrs) */
/* Should get_base_distance here, so we can check if any thing along
the path is virtual, and we need to make sure we stay inside the
real binfos when going through virtual bases. Maybe we should
replace virtual bases with BINFO_FOR_VBASE ... (mrs) */
binfo = get_binfo (from, to, 1);
if (binfo == error_mark_node)
{
......@@ -6010,7 +6009,7 @@ get_delta_difference (from, to, force)
return delta;
if (binfo_from_vbase (binfo))
{
binfo = BINFO_FOR_VBASE (BINFO_TYPE (binfo), from);
binfo = binfo_for_vbase (BINFO_TYPE (binfo), from);
cp_warning ("pointer to member cast to virtual base `%T' will only work if you are very careful", BINFO_TYPE (binfo));
}
delta = BINFO_OFFSET (binfo);
......
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