+1998-08-27 Jason Merrill <jason@yorick.cygnus.com>
+
+ Never change BINFO_INHERITANCE_CHAIN.
+ * init.c (emit_base_init): Change modification of
+ BINFO_INHERITANCE_CHAIN to an assert.
+ * search.c (get_base_distance_recursive): Likewise.
+ (get_base_distance): Likewise.
+ (lookup_member): Likewise.
+ (convert_pointer_to_single_level): Likewise.
+ (lookup_field): Likewise. Lose setting TREE_VIA_* on TREE_LISTs.
+ (lookup_fnfields): Likewise.
+ * tree.c (propagate_binfo_offsets): Don't call unshare_base_binfos.
+ (unshare_base_binfos): Don't call propagate_binfo_offsets.
+ (layout_basetypes): Call propagate_binfo_offsets instead of
+ unshare_base_binfos.
+ * decl.c (xref_basetypes): Call unshare_base_binfos.
+ * pt.c (instantiate_class_template): Likewise.
+ * tree.c (reverse_path): Remove 'copy' parm; always make a
+ temporary copy.
+ * class.c (build_vbase_path): Just call it.
+ * search.c (compute_access): Likewise. Don't re-reverse.
+
1998-08-27 Mark Mitchell <mark@markmitchell.com>
* class.c (build_vbase_path): Use reverse_path.
nonnull_expr = expr;
if (BINFO_INHERITANCE_CHAIN (path))
- {
- push_expression_obstack ();
- path = reverse_path (path, /*copy=*/1);
- pop_obstacks ();
- }
+ path = reverse_path (path);
basetype = BINFO_TYPE (path);
extern tree get_decl_list PROTO((tree));
extern tree make_binfo PROTO((tree, tree, tree, tree));
extern tree binfo_value PROTO((tree, tree));
-extern tree reverse_path PROTO((tree, int));
+extern tree reverse_path PROTO((tree));
extern int count_functions PROTO((tree));
extern int is_overloaded_fn PROTO((tree));
extern tree get_first_fn PROTO((tree));
TREE_VIA_VIRTUAL (base_binfo) = via_virtual;
BINFO_INHERITANCE_CHAIN (base_binfo) = TYPE_BINFO (ref);
+ /* We need to unshare the binfos now so that lookups during class
+ definition work. */
+ unshare_base_binfos (base_binfo);
+
SET_CLASSTYPE_MARKED (basetype);
/* We are free to modify these bits because they are meaningless
if (TREE_VIA_VIRTUAL (base_binfo))
continue;
-#if 0 /* Once unsharing happens soon enough. */
- my_friendly_assert (BINFO_INHERITANCE_CHAIN (base_binfo) == t_binfo, 999);
-#else
- BINFO_INHERITANCE_CHAIN (base_binfo) = t_binfo;
-#endif
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (base_binfo) == t_binfo,
+ 999);
if (TREE_PURPOSE (rbase_init_list))
init = TREE_VALUE (rbase_init_list);
/* These are set up in xref_basetypes for normal classes, so
we have to handle them here for template bases. */
+
+ unshare_base_binfos (elt);
+
if (TYPE_USES_VIRTUAL_BASECLASSES (basetype))
{
TYPE_USES_VIRTUAL_BASECLASSES (type) = 1;
current_scope_in_chain);
/* watch for updates; only update if path is good. */
if (path_ptr && WATCH_VALUES (rval, *via_virtual_ptr) != was)
- BINFO_INHERITANCE_CHAIN (base_binfo) = binfo;
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (base_binfo) == binfo,
+ 980827);
if (rval == -2 && *via_virtual_ptr == 0)
return rval;
binfo = TYPE_BINFO (type);
if (path_ptr)
- BINFO_INHERITANCE_CHAIN (binfo) = NULL_TREE;
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (binfo) == NULL_TREE,
+ 980827);
}
else
my_friendly_abort (92);
&& parent == binfo_member (BINFO_TYPE (parent),
CLASSTYPE_VBASECLASSES (type)))
{
- BINFO_INHERITANCE_CHAIN (parent) = binfo;
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (parent) == binfo, 980827);
new_binfo = parent;
rval = 1;
}
}
/* must reverse more than one element */
- basetype_path = reverse_path (basetype_path, /*copy=*/0);
+ basetype_path = reverse_path (basetype_path);
types = basetype_path;
via_protected = 0;
access = access_default_node;
else
break;
}
- reverse_path (basetype_path, /*copy=*/0);
/* No special visibilities apply. Use normal rules. */
{
type = xbasetype;
basetype_path = TYPE_BINFO (type);
- BINFO_INHERITANCE_CHAIN (basetype_path) = NULL_TREE;
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (basetype_path) == NULL_TREE,
+ 980827);
}
else
my_friendly_abort (97);
}
basetype_chain = build_expr_list (NULL_TREE, basetype_path);
- TREE_VIA_PUBLIC (basetype_chain) = TREE_VIA_PUBLIC (basetype_path);
- TREE_VIA_PROTECTED (basetype_chain) = TREE_VIA_PROTECTED (basetype_path);
- TREE_VIA_VIRTUAL (basetype_chain) = TREE_VIA_VIRTUAL (basetype_path);
/* The ambiguity check relies upon breadth first searching. */
SET_BINFO_FIELDS_MARKED (base_binfo);
btypes = my_tree_cons (NULL_TREE, base_binfo, basetype_chain);
- TREE_VIA_PUBLIC (btypes) = TREE_VIA_PUBLIC (base_binfo);
- TREE_VIA_PROTECTED (btypes) = TREE_VIA_PROTECTED (base_binfo);
- TREE_VIA_VIRTUAL (btypes) = TREE_VIA_VIRTUAL (base_binfo);
if (TREE_VIA_VIRTUAL (base_binfo))
btypes = my_tree_cons (NULL_TREE,
TYPE_BINFO (BINFO_TYPE (TREE_VEC_ELT (BINFO_BASETYPES (binfo_h), i))),
basetype_chain = TREE_CHAIN (basetype_chain);
basetype_path = TREE_VALUE (basetype_chain);
if (TREE_CHAIN (basetype_chain))
- BINFO_INHERITANCE_CHAIN (basetype_path) = TREE_VALUE (TREE_CHAIN (basetype_chain));
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (basetype_path)
+ == TREE_VALUE (TREE_CHAIN (basetype_chain)),
+ 980827);
else
- BINFO_INHERITANCE_CHAIN (basetype_path) = NULL_TREE;
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (basetype_path)
+ == NULL_TREE, 980827);
binfo = basetype_path;
type = BINFO_TYPE (binfo);
if (basetype_path == TYPE_BINFO (type))
{
basetype_chain = CLASSTYPE_BINFO_AS_LIST (type);
- TREE_VIA_PUBLIC (basetype_chain) = 1;
- BINFO_INHERITANCE_CHAIN (basetype_path) = NULL_TREE;
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (basetype_path) == NULL_TREE,
+ 980827);
}
else
- {
- basetype_chain = build_expr_list (NULL_TREE, basetype_path);
- TREE_VIA_PUBLIC (basetype_chain) = TREE_VIA_PUBLIC (basetype_path);
- TREE_VIA_PROTECTED (basetype_chain) = TREE_VIA_PROTECTED (basetype_path);
- TREE_VIA_VIRTUAL (basetype_chain) = TREE_VIA_VIRTUAL (basetype_path);
- }
+ basetype_chain = build_expr_list (NULL_TREE, basetype_path);
/* The ambiguity check relies upon breadth first searching. */
SET_BINFO_FIELDS_MARKED (base_binfo);
btypes = my_tree_cons (NULL_TREE, base_binfo, basetype_chain);
- TREE_VIA_PUBLIC (btypes) = TREE_VIA_PUBLIC (base_binfo);
- TREE_VIA_PROTECTED (btypes) = TREE_VIA_PROTECTED (base_binfo);
- TREE_VIA_VIRTUAL (btypes) = TREE_VIA_VIRTUAL (base_binfo);
if (TREE_VIA_VIRTUAL (base_binfo))
btypes = my_tree_cons (NULL_TREE,
TYPE_BINFO (BINFO_TYPE (TREE_VEC_ELT (BINFO_BASETYPES (binfo_h), i))),
basetype_chain = TREE_CHAIN (basetype_chain);
basetype_path = TREE_VALUE (basetype_chain);
if (TREE_CHAIN (basetype_chain))
- BINFO_INHERITANCE_CHAIN (basetype_path) = TREE_VALUE (TREE_CHAIN (basetype_chain));
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (basetype_path)
+ == TREE_VALUE (TREE_CHAIN (basetype_chain)),
+ 980827);
else
- BINFO_INHERITANCE_CHAIN (basetype_path) = NULL_TREE;
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (basetype_path)
+ == NULL_TREE, 980827);
binfo = basetype_path;
type = BINFO_TYPE (binfo);
else if (IS_AGGR_TYPE_CODE (TREE_CODE (xbasetype)))
{
basetype_path = TYPE_BINFO (xbasetype);
- BINFO_INHERITANCE_CHAIN (basetype_path) = NULL_TREE;
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (basetype_path)
+ == NULL_TREE, 980827);
}
else
my_friendly_abort (97);
binfo_of_derived = TYPE_BINFO (TREE_TYPE (TREE_TYPE (expr)));
last = get_binfo (to_type, TREE_TYPE (TREE_TYPE (expr)), 0);
- BINFO_INHERITANCE_CHAIN (last) = binfo_of_derived;
- BINFO_INHERITANCE_CHAIN (binfo_of_derived) = NULL_TREE;
- return build_vbase_path (PLUS_EXPR, build_pointer_type (to_type), expr, last, 1);
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (last) == binfo_of_derived,
+ 980827);
+ my_friendly_assert (BINFO_INHERITANCE_CHAIN (binfo_of_derived) == NULL_TREE,
+ 980827);
+ return build_vbase_path (PLUS_EXPR, build_pointer_type (to_type), expr,
+ last, 1);
}
/* The main function which implements depth first search.
static tree list_hash_lookup PROTO((int, int, int, int, tree, tree,
tree));
static void propagate_binfo_offsets PROTO((tree, tree));
-static void unshare_base_binfos PROTO((tree));
static int avoid_overlap PROTO((tree, tree));
#define CEIL(x,y) (((x) + (y) - 1) / (y))
tree base_binfo = TREE_VEC_ELT (binfos, i);
if (TREE_VIA_VIRTUAL (base_binfo))
- {
- i += 1;
- unshare_base_binfos (base_binfo);
- }
+ i += 1;
else
{
int j;
BINFO_OFFSET (base_binfo) = offset;
#endif
- unshare_base_binfos (base_binfo);
+ propagate_binfo_offsets (base_binfo, offset);
/* Go to our next class that counts for offset propagation. */
i = j;
}
}
-/* Makes new binfos for the indirect bases under BASE_BINFO, and updates
+/* Makes new binfos for the indirect bases under BINFO, and updates
BINFO_OFFSET for them and their bases. */
-static void
-unshare_base_binfos (base_binfo)
- tree base_binfo;
+void
+unshare_base_binfos (binfo)
+ tree binfo;
{
- if (BINFO_BASETYPES (base_binfo))
- {
- tree base_binfos = BINFO_BASETYPES (base_binfo);
- tree chain = NULL_TREE;
- int j;
+ tree binfos = BINFO_BASETYPES (binfo);
+ tree new_binfo;
+ int j;
- /* Now unshare the structure beneath BASE_BINFO. */
- for (j = TREE_VEC_LENGTH (base_binfos)-1;
- j >= 0; j--)
- {
- tree base_base_binfo = TREE_VEC_ELT (base_binfos, j);
- TREE_VEC_ELT (base_binfos, j)
- = make_binfo (BINFO_OFFSET (base_base_binfo),
- base_base_binfo,
- BINFO_VTABLE (base_base_binfo),
- BINFO_VIRTUALS (base_base_binfo));
- chain = TREE_VEC_ELT (base_binfos, j);
- TREE_VIA_PUBLIC (chain) = TREE_VIA_PUBLIC (base_base_binfo);
- TREE_VIA_PROTECTED (chain) = TREE_VIA_PROTECTED (base_base_binfo);
- TREE_VIA_VIRTUAL (chain) = TREE_VIA_VIRTUAL (base_base_binfo);
- BINFO_INHERITANCE_CHAIN (chain) = base_binfo;
- }
+ if (binfos == NULL_TREE)
+ return;
- /* Completely unshare potentially shared data, and
- update what is ours. */
- propagate_binfo_offsets (base_binfo, BINFO_OFFSET (base_binfo));
+ /* Now unshare the structure beneath BINFO. */
+ for (j = TREE_VEC_LENGTH (binfos)-1;
+ j >= 0; j--)
+ {
+ tree base_binfo = TREE_VEC_ELT (binfos, j);
+ new_binfo = TREE_VEC_ELT (binfos, j)
+ = make_binfo (BINFO_OFFSET (base_binfo),
+ base_binfo,
+ BINFO_VTABLE (base_binfo),
+ BINFO_VIRTUALS (base_binfo));
+ TREE_VIA_PUBLIC (new_binfo) = TREE_VIA_PUBLIC (base_binfo);
+ TREE_VIA_PROTECTED (new_binfo) = TREE_VIA_PROTECTED (base_binfo);
+ TREE_VIA_VIRTUAL (new_binfo) = TREE_VIA_VIRTUAL (base_binfo);
+ BINFO_INHERITANCE_CHAIN (new_binfo) = binfo;
+ unshare_base_binfos (new_binfo);
}
}
tree field = TYPE_FIELDS (rec);
if (TREE_VIA_VIRTUAL (base_binfo))
- unshare_base_binfos (base_binfo);
- else
- {
- my_friendly_assert (TREE_TYPE (field) == basetype, 23897);
+ continue;
- if (get_base_distance (basetype, rec, 0, (tree*)0) == -2)
- cp_warning ("direct base `%T' inaccessible in `%T' due to ambiguity",
- basetype, rec);
+ my_friendly_assert (TREE_TYPE (field) == basetype, 23897);
- BINFO_OFFSET (base_binfo)
- = size_int (CEIL (TREE_INT_CST_LOW (DECL_FIELD_BITPOS (field)),
- BITS_PER_UNIT));
- unshare_base_binfos (base_binfo);
- TYPE_FIELDS (rec) = TREE_CHAIN (field);
- }
+ if (get_base_distance (basetype, rec, 0, (tree*)0) == -2)
+ cp_warning ("direct base `%T' inaccessible in `%T' due to ambiguity",
+ basetype, rec);
+
+ BINFO_OFFSET (base_binfo)
+ = size_int (CEIL (TREE_INT_CST_LOW (DECL_FIELD_BITPOS (field)),
+ BITS_PER_UNIT));
+ propagate_binfo_offsets (base_binfo, BINFO_OFFSET (base_binfo));
+ TYPE_FIELDS (rec) = TREE_CHAIN (field);
}
for (vbase_types = CLASSTYPE_VBASECLASSES (rec); vbase_types;
{
BINFO_INHERITANCE_CHAIN (vbase_types) = TYPE_BINFO (rec);
unshare_base_binfos (vbase_types);
+ propagate_binfo_offsets (vbase_types, BINFO_OFFSET (vbase_types));
if (extra_warnings)
{
return get_binfo (elem, type, 0);
}
-/* Reverse the BINFO-chain given by PATH. (If the
+/* Return a reversed copy of the BINFO-chain given by PATH. (If the
BINFO_INHERITANCE_CHAIN points from base classes to derived
classes, it will instead point from derived classes to base
- classes.) Returns the first node in the reversed chain. If COPY
- is non-zero, the nodes are copied as the chain is traversed. */
+ classes.) Returns the first node in the reversed chain. */
tree
-reverse_path (path, copy)
+reverse_path (path)
tree path;
- int copy;
{
- register tree prev = 0, tmp, next;
- for (tmp = path; tmp; tmp = next)
+ register tree prev = NULL_TREE, cur;
+ push_expression_obstack ();
+ for (cur = path; cur; cur = BINFO_INHERITANCE_CHAIN (cur))
{
- if (copy)
- tmp = copy_node (tmp);
- next = BINFO_INHERITANCE_CHAIN (tmp);
- BINFO_INHERITANCE_CHAIN (tmp) = prev;
- prev = tmp;
+ tree r = copy_node (cur);
+ BINFO_INHERITANCE_CHAIN (r) = prev;
+ prev = r;
}
+ pop_obstacks ();
return prev;
}