diff options
author | paolo <paolo@138bc75d-0d04-0410-961f-82ee72b054a4> | 2013-09-02 09:42:39 +0000 |
---|---|---|
committer | paolo <paolo@138bc75d-0d04-0410-961f-82ee72b054a4> | 2013-09-02 09:42:39 +0000 |
commit | 894d126ec11fa17fb616f28a1555992560b9dd07 (patch) | |
tree | ba3527b81eff0d88a2b16e3a9590ef37de65994b /gcc/cp/name-lookup.c | |
parent | 0a3fd7ce64e8e0098411ae728253299d9d686aab (diff) | |
download | gcc-894d126ec11fa17fb616f28a1555992560b9dd07.tar.gz |
/cp
2013-09-02 Paolo Carlini <paolo.carlini@oracle.com>
PR c++/21682, implement DR 565
* name-lookup.c (compparms_for_decl_and_using_decl): New.
(push_overloaded_decl_1, do_nonmember_using_decl): Use it.
/testsuite
2013-09-02 Paolo Carlini <paolo.carlini@oracle.com>
PR c++/21682, implement DR 565
* g++.dg/template/using24.C: New.
* g++.dg/template/using25.C: Likewise.
* g++.dg/template/using26.C: Likewise.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@202163 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/cp/name-lookup.c')
-rw-r--r-- | gcc/cp/name-lookup.c | 27 |
1 files changed, 23 insertions, 4 deletions
diff --git a/gcc/cp/name-lookup.c b/gcc/cp/name-lookup.c index b09e85bcb66..025a03cd9fa 100644 --- a/gcc/cp/name-lookup.c +++ b/gcc/cp/name-lookup.c @@ -2267,6 +2267,27 @@ pushdecl_with_scope (tree x, cp_binding_level *level, bool is_friend) return ret; } +/* Helper function for push_overloaded_decl_1 and do_nonmember_using_decl. + Compares the parameter-type-lists of DECL1 and DECL2 and returns false + if they are different. If the DECLs are template functions, the return + types and the template parameter lists are compared too (DR 565). */ + +static bool +compparms_for_decl_and_using_decl (tree decl1, tree decl2) +{ + if (!compparms (TYPE_ARG_TYPES (TREE_TYPE (decl1)), + TYPE_ARG_TYPES (TREE_TYPE (decl2)))) + return false; + + if (! DECL_FUNCTION_TEMPLATE_P (decl1) + || ! DECL_FUNCTION_TEMPLATE_P (decl2)) + return true; + + return (comp_template_parms (DECL_TEMPLATE_PARMS (decl1), + DECL_TEMPLATE_PARMS (decl2)) + && same_type_p (TREE_TYPE (TREE_TYPE (decl1)), + TREE_TYPE (TREE_TYPE (decl2)))); +} /* DECL is a FUNCTION_DECL for a non-member function, which may have other definitions already in place. We get around this by making @@ -2324,8 +2345,7 @@ push_overloaded_decl_1 (tree decl, int flags, bool is_friend) if (TREE_CODE (tmp) == OVERLOAD && OVL_USED (tmp) && !(flags & PUSH_USING) - && compparms (TYPE_ARG_TYPES (TREE_TYPE (fn)), - TYPE_ARG_TYPES (TREE_TYPE (decl))) + && compparms_for_decl_and_using_decl (fn, decl) && ! decls_match (fn, decl)) diagnose_name_conflict (decl, fn); @@ -2561,8 +2581,7 @@ do_nonmember_using_decl (tree scope, tree name, tree oldval, tree oldtype, break; else if (TREE_CODE (tmp1) == OVERLOAD && OVL_USED (tmp1)) continue; /* this is a using decl */ - else if (compparms (TYPE_ARG_TYPES (TREE_TYPE (new_fn)), - TYPE_ARG_TYPES (TREE_TYPE (old_fn)))) + else if (compparms_for_decl_and_using_decl (new_fn, old_fn)) { gcc_assert (!DECL_ANTICIPATED (old_fn) || DECL_HIDDEN_FRIEND_P (old_fn)); |