From ed70c42623729d86d2dc610a5279a5f394be68ee Mon Sep 17 00:00:00 2001 From: Mark Mitchell Date: Fri, 26 Feb 1999 12:00:10 +0000 Subject: [PATCH] class.c (check_for_override): Don't stop checking when we find the first overridden function. * class.c (check_for_override): Don't stop checking when we find the first overridden function. Delete #if 0'd code. * search.c (get_matching_virtual): Likewise. From-SVN: r25457 --- gcc/cp/ChangeLog | 6 +++++ gcc/cp/class.c | 31 ++++++++++--------------- gcc/cp/search.c | 14 +++++------ gcc/testsuite/g++.old-deja/g++.other/virtual4.C | 25 ++++++++++++++++++++ 4 files changed, 50 insertions(+), 26 deletions(-) create mode 100644 gcc/testsuite/g++.old-deja/g++.other/virtual4.C diff --git a/gcc/cp/ChangeLog b/gcc/cp/ChangeLog index b0ef37c..e9f87d7 100644 --- a/gcc/cp/ChangeLog +++ b/gcc/cp/ChangeLog @@ -1,3 +1,9 @@ +1999-02-26 Mark Mitchell + + * class.c (check_for_override): Don't stop checking when we find + the first overridden function. Delete #if 0'd code. + * search.c (get_matching_virtual): Likewise. + 1999-02-25 Richard Henderson * lang-specs.h: Define __FAST_MATH__ when appropriate. diff --git a/gcc/cp/class.c b/gcc/cp/class.c index 7e91612..3fc9cf4 100644 --- a/gcc/cp/class.c +++ b/gcc/cp/class.c @@ -2991,6 +2991,7 @@ check_for_override (decl, ctype) tree binfos = BINFO_BASETYPES (TYPE_BINFO (ctype)); int i, n_baselinks = binfos ? TREE_VEC_LENGTH (binfos) : 0; int virtualp = DECL_VIRTUAL_P (decl); + int found_overriden_fn = 0; for (i = 0; i < n_baselinks; i++) { @@ -3000,7 +3001,8 @@ check_for_override (decl, ctype) tree tmp = get_matching_virtual (base_binfo, decl, DESTRUCTOR_NAME_P (DECL_ASSEMBLER_NAME (decl))); - if (tmp) + + if (tmp && !found_overriden_fn) { /* If this function overrides some virtual in some base class, then the function itself is also necessarily @@ -3021,26 +3023,15 @@ check_for_override (decl, ctype) } virtualp = 1; -#if 0 /* The signature of an overriding function is not changed. */ - { - /* The argument types may have changed... */ - tree type = TREE_TYPE (decl); - tree argtypes = TYPE_ARG_TYPES (type); - tree base_variant = TREE_TYPE (TREE_VALUE (argtypes)); - tree raises = TYPE_RAISES_EXCEPTIONS (type); - - argtypes = commonparms (TREE_CHAIN (TYPE_ARG_TYPES (TREE_TYPE (tmp))), - TREE_CHAIN (argtypes)); - /* But the return type has not. */ - type = build_cplus_method_type (base_variant, TREE_TYPE (type), argtypes); - if (raises) - type = build_exception_variant (type, raises); - TREE_TYPE (decl) = type; - } -#endif DECL_VINDEX (decl) = tree_cons (NULL_TREE, tmp, DECL_VINDEX (decl)); - break; + + /* We now know that DECL overrides something, + which is all that is important. But, we must + continue to iterate through all the base-classes + in order to allow get_matching_virtual to check for + various illegal overrides. */ + found_overriden_fn = 1; } } } @@ -4897,6 +4888,8 @@ push_nested_class (type, modify) { tree context; + my_friendly_assert (!type || TREE_CODE (type) != NAMESPACE_DECL, 980711); + /* A namespace might be passed in error cases, like A::B:C. */ if (type == NULL_TREE || type == error_mark_node || ! IS_AGGR_TYPE (type) || TREE_CODE (type) == NAMESPACE_DECL diff --git a/gcc/cp/search.c b/gcc/cp/search.c index 33842c6..6c046ed 100644 --- a/gcc/cp/search.c +++ b/gcc/cp/search.c @@ -1887,15 +1887,15 @@ get_matching_virtual (binfo, fndecl, dtorp) cp_error_at (" overriding definition as `%#D'", tmp); SET_IDENTIFIER_ERROR_LOCUS (name, basetype); } - break; + + /* FNDECL overrides this function. We continue to + check all the other functions in order to catch + errors; it might be that in some other baseclass + a virtual function was declared with the same + parameter types, but a different return type. */ + best = tmp; } } - /* If not at the end */ - if (tmps) - { - best = tmp; - break; - } } return best; diff --git a/gcc/testsuite/g++.old-deja/g++.other/virtual4.C b/gcc/testsuite/g++.old-deja/g++.other/virtual4.C new file mode 100644 index 0000000..8a44ee1 --- /dev/null +++ b/gcc/testsuite/g++.old-deja/g++.other/virtual4.C @@ -0,0 +1,25 @@ +// Build don't link: + +class A { +public: + virtual int foo() = 0; // ERROR - original definition +}; + +class B { +public: + virtual double foo() = 0; +}; + +class C + : public A, public B +{ +public: + virtual double foo() { return 2; } // ERROR - conflicting return type +}; + +class D + : public B, public A +{ +public: + virtual double foo() { return 2; } // ERROR - conflicting return type +}; -- 2.7.4