Commit 8d1f0f67 by Jason Merrill Committed by Jason Merrill

re PR c++/5607 (No pointer adjustment in covariant return types)

        PR c++/5607
        * search.c (check_final_overrider): No longer static.
        * class.c (update_vtable_entry_for_fn): Call it.
        * cp-tree.h: Adjust.

From-SVN: r52760
parent ab5973b7
2002-04-25 Jason Merrill <jason@redhat.com>
PR c++/5607
* search.c (check_final_overrider): No longer static.
* class.c (update_vtable_entry_for_fn): Call it.
* cp-tree.h: Adjust.
2002-04-25 Neil Booth <neil@daikokuya.demon.co.uk> 2002-04-25 Neil Booth <neil@daikokuya.demon.co.uk>
* cp-lang.c (LANG_HOOKS_SET_YYDEBUG): Remove. * cp-lang.c (LANG_HOOKS_SET_YYDEBUG): Remove.
......
...@@ -2555,6 +2555,10 @@ update_vtable_entry_for_fn (t, binfo, fn, virtuals) ...@@ -2555,6 +2555,10 @@ update_vtable_entry_for_fn (t, binfo, fn, virtuals)
if (overrider == error_mark_node) if (overrider == error_mark_node)
return; return;
/* Check for unsupported covariant returns again now that we've
calculated the base offsets. */
check_final_overrider (TREE_PURPOSE (overrider), fn);
/* Assume that we will produce a thunk that convert all the way to /* Assume that we will produce a thunk that convert all the way to
the final overrider, and not to an intermediate virtual base. */ the final overrider, and not to an intermediate virtual base. */
virtual_base = NULL_TREE; virtual_base = NULL_TREE;
......
...@@ -4098,6 +4098,7 @@ extern tree lookup_conversions PARAMS ((tree)); ...@@ -4098,6 +4098,7 @@ extern tree lookup_conversions PARAMS ((tree));
extern tree binfo_for_vtable PARAMS ((tree)); extern tree binfo_for_vtable PARAMS ((tree));
extern tree binfo_from_vbase PARAMS ((tree)); extern tree binfo_from_vbase PARAMS ((tree));
extern tree look_for_overrides_here PARAMS ((tree, tree)); extern tree look_for_overrides_here PARAMS ((tree, tree));
extern int check_final_overrider PARAMS ((tree, tree));
extern tree dfs_walk PARAMS ((tree, extern tree dfs_walk PARAMS ((tree,
tree (*) (tree, void *), tree (*) (tree, void *),
tree (*) (tree, void *), tree (*) (tree, void *),
......
...@@ -100,7 +100,6 @@ static tree dfs_push_decls PARAMS ((tree, void *)); ...@@ -100,7 +100,6 @@ static tree dfs_push_decls PARAMS ((tree, void *));
static tree dfs_unuse_fields PARAMS ((tree, void *)); static tree dfs_unuse_fields PARAMS ((tree, void *));
static tree add_conversions PARAMS ((tree, void *)); static tree add_conversions PARAMS ((tree, void *));
static int covariant_return_p PARAMS ((tree, tree)); static int covariant_return_p PARAMS ((tree, tree));
static int check_final_overrider PARAMS ((tree, tree));
static int look_for_overrides_r PARAMS ((tree, tree)); static int look_for_overrides_r PARAMS ((tree, tree));
static struct search_level *push_search_level static struct search_level *push_search_level
PARAMS ((struct stack_level *, struct obstack *)); PARAMS ((struct stack_level *, struct obstack *));
...@@ -1798,7 +1797,7 @@ covariant_return_p (brettype, drettype) ...@@ -1798,7 +1797,7 @@ covariant_return_p (brettype, drettype)
/* Check that virtual overrider OVERRIDER is acceptable for base function /* Check that virtual overrider OVERRIDER is acceptable for base function
BASEFN. Issue diagnostic, and return zero, if unacceptable. */ BASEFN. Issue diagnostic, and return zero, if unacceptable. */
static int int
check_final_overrider (overrider, basefn) check_final_overrider (overrider, basefn)
tree overrider, basefn; tree overrider, basefn;
{ {
......
// PR c++/5607
// Currently we don't support covariant returns that would actually require
// a pointer adjustment. We were failing to recognize this as such a case,
// so were silently generating bad code. When we do support covariant
// returns properly, the expected error should go away, and the testcase
// should pass execution.
// { NOT YET dg-do run }
class A {
public:
virtual A* getThis() { return this; }
};
class B {
int a;
public:
virtual B* getThis() { return this; }
};
class AB : public A, public B { // { dg-error "covariant" }
public:
virtual AB* getThis() { return this; }
};
int main ()
{
AB* ab = new AB();
A* a = ab;
B* b = ab;
if (a->getThis() != a
|| b->getThis() != b)
return 1;
return 0;
}
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